Ticket #11: exception.3.diff

File exception.3.diff, 81.3 KB (added by Nicolas Pouillon, 15 years ago)

Same, improved with PPC support, tried & tested through automated builds, with correct ARM init

  • cpu/arm/exception.c

     
     1/*
     2    This file is part of MutekH.
     3
     4    MutekH is free software; you can redistribute it and/or modify it
     5    under the terms of the GNU General Public License as published by
     6    the Free Software Foundation; either version 2 of the License, or
     7    (at your option) any later version.
     8
     9    MutekH is distributed in the hope that it will be useful, but
     10    WITHOUT ANY WARRANTY; without even the implied warranty of
     11    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
     12    General Public License for more details.
     13
     14    You should have received a copy of the GNU General Public License
     15    along with MutekH; if not, write to the Free Software Foundation,
     16    Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
     17
     18    Copyright (c) 2010, Nicolas Pouillon <nipo@ssji.net>
     19*/
     20
     21#include <hexo/asm.h>
     22#include <hexo/interrupt.h>
     23
     24#define GET_OP2REL(name, rd, rt, op2)                                  \
     25    "ldr  " rd ", =" name "             \n\t"                          \
     26    "mrc p15,0," rt ",c13,c0," #op2 "   \n\t"                          \
     27    "ldr  " rd ", [" rd ", +" rt "]     \n\t"
     28#define GET_ABS(name, rd)                                              \
     29    "ldr  " rd ", =" name "     \n\t"                                  \
     30    "ldr  " rd ", [" rd "]      \n\t"
     31
     32#ifdef CONFIG_SMP
     33# define CPULOCAL_GET(name, rd, rt) GET_OP2REL(name, rd, rt, 3)
     34#else
     35# define CPULOCAL_GET(name, rd, rt) GET_ABS(name, rd)
     36#endif
     37
     38#define CONTEXTLOCAL_GET(name, rd, rt) GET_OP2REL(name, rd, rt, 4)
     39
     40#define SUB_0
     41#define SUB_4 "sub    lr, lr, #4 \n\t"
     42#define SUB_8 "sub    lr, lr, #8 \n\t"
     43
     44asm(
     45    ".section        .text,\"ax\"         \n"
     46
     47#define prepare_exception(pc_offset)                                   \
     48    /* uniformize return address, but avoid a sub when 0 */            \
     49    SUB_##pc_offset                                                    \
     50    /* store r0 and exc pc in tmp buffer */                            \
     51    "stmia  sp, {r0, r1, lr}      \n\t"                                \
     52    /* Take old msr, save it */                                        \
     53    "mrs    r0, spsr              \n\t"                                \
     54    "str    r0, [sp, #12]         \n\t"                                \
     55    /* take pointer to tmp buffer */                                   \
     56    "mov    r1, sp                \n\t"                                \
     57    /* disable irqs, switch to supervisor */                           \
     58    "bic    r0, r0, #0xff         \n\t"                                \
     59    "orr    r0, r0, #0xd3         \n\t"                                \
     60    "msr    cpsr, r0              \n\t"
     61
     62#define restore_exception()                                            \
     63    /*                                                                 \
     64     * Here we're back with tmp buf in r1,                             \
     65     * all registers but r0/r1 should already be restored.             \
     66     */                                                                \
     67    /* restore spsr */                                                 \
     68    "ldr    r0, [r1, #12]         \n\t"                                \
     69    "msr    spsr, r0              \n\t"                                \
     70    /* restore regs */                                                 \
     71    "ldmia  r1, {r0, r1, lr}      \n\t"                                \
     72    /* jump back, sp is in target mode. */                             \
     73    "movs   pc, lr                \n\t"
     74
     75#define handle_exception(arg)                                          \
     76    "mov    r0, #" ASM_STR(arg) " \n\t"                                \
     77    "b      arm_exc_common        \n\t"
     78
     79#define handle_irq(no)                                                 \
     80    "mov    r0, #" #no "          \n\t"                                \
     81    "b      arm_irq_common        \n\t"
     82
     83    /* r14 is exc pc + 4 */
     84    FUNC_START(arm_exc_undef)
     85    prepare_exception(4)
     86    handle_exception(CPU_EXCEPTION_ILLEGAL_INS)
     87    FUNC_END(arm_exc_undef)
     88
     89    /* r14 is error pc + 4 */
     90    FUNC_START(arm_exc_pabt)
     91    prepare_exception(4)
     92    handle_exception(CPU_EXCEPTION_INS_ERROR)
     93    FUNC_END(arm_exc_pabt)
     94
     95    /* r14 is error pc + 8 */
     96    FUNC_START(arm_exc_dabt)
     97    prepare_exception(8)
     98    handle_exception(CPU_EXCEPTION_DATA_ERROR)
     99    FUNC_END(arm_exc_dabt)
     100
     101#if !defined(CONFIG_CPU_ARM_CUSTOM_IRQ_HANDLER)
     102    /* r14 is error pc + 4 */
     103    FUNC_START(arm_exc_irq)
     104    prepare_exception(4)
     105    handle_irq(0)
     106    FUNC_END(arm_exc_irq)
     107
     108    /* r14 is error pc + 4 */
     109    FUNC_START(arm_exc_fiq)
     110    prepare_exception(4)
     111    handle_irq(1)
     112    FUNC_END(arm_exc_fiq)
     113#endif
     114
     115    /* r14 is swi pc + 4 */
     116    FUNC_START(arm_exc_swi)
     117    prepare_exception(0)
     118    "push  {r1}                    \n\t"
     119    "push  {r2, r3, ip}            \n\t"
     120    /* get r0/r1 and put them on stack */
     121    "ldmia r1, {r2, r3}            \n\t"
     122    "push  {r2, r3}                \n\t"
     123    /* stack is [r0, r1, r2, r3, ip, tmp] */
     124    CONTEXTLOCAL_GET("cpu_syscall_handler", "ip", "r2")
     125    /* get swi instruction */
     126    "ldr   r0, [r1, #8]            \n\t"
     127    "ldr   r0, [r0, #-4]           \n\t"
     128    /* r0: masked opcode */
     129    "bic   r0, #0xff000000         \n\t"
     130    /* r1: regtable pointer */
     131    "mov   r1, sp                  \n\t"
     132    /* call handler */
     133    "mov   lr, pc                  \n\t"
     134    "bx    ip                      \n\t"
     135    /* stack is [r0, r1, r2, r3, ip, tmp] */
     136    /* reget tmp buf */
     137    "ldr   r1, [sp, #20]           \n\t"
     138    /* put back r0/r1 to tmp buf */
     139    "pop   {r2, r3}                \n\t"
     140    "stmia r1, {r2, r3}            \n\t"
     141    /* restore, return */
     142    "pop   {r2, r3, ip}            \n\t"
     143    "pop   {r1}                    \n\t"
     144    restore_exception()
     145    FUNC_END(arm_exc_swi)
     146
     147    FUNC_START(arm_exc_common)
     148    "push  {r1}                    \n\t"
     149    "push  {r2, r3, ip}            \n\t"
     150    /* get r0/r1 and put them on stack */
     151    "ldmia r1, {r2, r3}            \n\t"
     152    "push  {r2, r3}                \n\t"
     153    /* stack is [r0, r1, r2, r3, ip, tmp] */
     154
     155    /* Put handler arguments: */
     156    /* a0: type, already done */
     157    /* a1: execptr, from [r1, #8] */
     158    /* a2: dataptr (argh! this is machine dep!) */
     159    /* a3: regtable */
     160    /* *sp: sp when faulted */
     161    CPULOCAL_GET("cpu_exception_handler", "ip", "r2")
     162    /* push sp ... */
     163#if defined(CONFIG_USER_MODE)
     164    /* test whether from user mode */
     165    "ldr   r2, [r1, #12]           \n\t"
     166    "ands  r2, r2, #f              \n\t"
     167    /* sp from kernel, 6 words away */
     168    "addne r2, sp, #6*4            \n\t"
     169    "pushne {r2}                   \n\t"
     170    /* sp from user */
     171    "pusheq {sp}^                  \n\t"
     172#else
     173    /* sp is 6 words away */
     174    "add   r2, sp, #6*4            \n\t"
     175    "push  {r2}                    \n\t"
     176#endif
     177    /* a1 */
     178    "ldr   r1, [r1, #8]            \n\t"
     179    /* a2 */
     180#if defined(CONFIG_ARCH_SIMPLE_SAM7)
     181    "ldr   r2, =0xffffff08         \n\t"
     182    "ldr   r2, [r2]                \n\t"
     183#elif defined(CONFIG_CPU_ARM_SOCLIB)
     184    "mrc p15, 0, r2, c6, c0, 0     \n\t"
     185#else
     186# warning No way to get data error pointer !
     187    "ldr   r2, =0xbad0da1a         \n\t"
     188#endif
     189    /* a3 */
     190    "add   r3, sp, #4              \n\t"
     191    /* call handler */
     192    "mov   lr, pc                  \n\t"
     193    "bx    ip                      \n\t"
     194
     195    /* stack is [sp, r0, r1, r2, r3, ip, tmp] */
     196
     197    /* remove sp */
     198    "add   sp, sp, #4              \n\t"
     199
     200    /* reget tmp buf */
     201    "ldr   r1, [sp, #20]           \n\t"
     202    /* put back r0/r1 to tmp buf */
     203    "pop   {r2, r3}                \n\t"
     204    "stmia r1, {r2, r3}            \n\t"
     205    /* restore, return */
     206    "pop   {r2, r3, ip}            \n\t"
     207    "pop   {r1}                    \n\t"
     208    restore_exception()
     209    FUNC_END(arm_exc_common)
     210
     211
     212#if !defined(CONFIG_CPU_ARM_CUSTOM_IRQ_HANDLER)
     213    FUNC_START(arm_irq_common)
     214    "push  {r1, r2, r3, ip}        \n\t"
     215    /* Put handler arguments: */
     216    /* a0: priv */
     217    /* a1: irq */
     218    "mov   r1, r0                  \n\t"
     219    CPULOCAL_GET("cpu_interrupt_handler_arg", "r0", "r3")
     220    CPULOCAL_GET("cpu_interrupt_handler",     "ip", "r3")
     221    "mov   lr, pc                  \n\t"
     222    "bx    ip                      \n\t"
     223    "pop   {r1, r2, r3, ip}        \n\t"
     224    restore_exception()
     225    FUNC_END(arm_irq_common)
     226#endif
     227
     228    );
     229
     230// Local Variables:
     231// tab-width: 4;
     232// c-basic-offset: 4;
     233// indent-tabs-mode: nil;
     234// End:
     235//
     236// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=4:softtabstop=4
  • cpu/arm/boot_m.c

    Property changes on: cpu/arm/exception.c
    ___________________________________________________________________
    Added: svn:mime-type
       + text/plain
    Added: svn:keywords
       + "Author Date Id Rev URL Revision"
    Added: svn:eol-style
       + native
    
     
    1 /*
    2     This file is part of MutekH.
    3 
    4     MutekH is free software; you can redistribute it and/or modify it
    5     under the terms of the GNU General Public License as published by
    6     the Free Software Foundation; either version 2 of the License, or
    7     (at your option) any later version.
    8 
    9     MutekH is distributed in the hope that it will be useful, but
    10     WITHOUT ANY WARRANTY; without even the implied warranty of
    11     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
    12     General Public License for more details.
    13 
    14     You should have received a copy of the GNU General Public License
    15     along with MutekH; if not, write to the Free Software Foundation,
    16     Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
    17 
    18     Copyright (c) Nicolas Pouillon <nipo@ssji.net>, 2009
    19 
    20 */
    21 
    22 #if CONFIG_SMP
    23 # error No SMP supported
    24 #endif
    25 
    26 # define GET_HANDLER_ADDRESS(name, rd, rt, foo)                                            \
    27         "ldr  " rt ", =" name "     \n\t"                                                                  \
    28         "ldr  " rd ", [" rt "]      \n\t"
    29 
    30 # define GET_CPULOCAL_HANDLER_ADDRESS(name, rd, rt) GET_HANDLER_ADDRESS(name, rd, rt, 3)
    31 # define GET_CONTEXTLOCAL_HANDLER_ADDRESS(name, rd, rt) GET_HANDLER_ADDRESS(name, rd, rt, 4)
    32 
    33 
    34 asm(
    35     ".section        .boot,\"ax\"       \n"
    36 
    37     ".globl cpu_boot                            \n\t"
    38     ".func cpu_boot                                 \n\t"
    39         ".type   cpu_boot, %function    \n\t"
    40         "cpu_boot:                      \n\t"
    41         "ldr pc, =arm_boot                     \n\t"
    42         "ldr pc, =arm_c_exc_undef                \n\t"
    43 
    44 /*      "ldr pc, =arm_c_exc_swi                  \n\t" */
    45         "nop                                   \n\t"
    46 /*      "ldr pc, =arm_c_exc_pabt                 \n\t" */
    47         "nop                                   \n\t"
    48 /*      "ldr pc, =arm_c_exc_dabt                 \n\t" */
    49         "nop                                   \n\t"
    50 
    51         "nop                                   \n\t"
    52         "ldr pc, =arm_c_irq_handler           \n\t"
    53         "ldr pc, =arm_c_fiq_handler           \n\t"
    54         ".size   cpu_boot, .-cpu_boot   \n\t"
    55         ".endfunc \n\t"
    56 
    57     ".globl arm_boot                              \n\t"
    58     ".func  arm_boot                              \n\t"
    59         ".type   arm_boot, %function      \n\t"
    60         "arm_boot:                        \n\t"
    61         /* set stack */
    62     "ldr  r13, =__initial_stack-16  \n\t"
    63 
    64     /* Get the device tree and put it in first arg */
    65 #ifdef CONFIG_ARCH_DEVICE_TREE
    66     "ldr  r0, =dt_blob_start          \n\t"
    67 #else
    68     "mov  r0, #0                      \n\t"
    69 #endif
    70     /* Put a 0 in second arg */
    71     "mov  r1, #0                      \n\t"
    72 
    73         /* jump to arch_init */
    74     "ldr   r5, =arch_init             \n\t"
    75         "bx    r5                         \n\t"
    76         ".size   arm_boot, .-arm_boot     \n\t"
    77         ".endfunc \n\t"
    78 
    79         );
  • cpu/arm/include/cpu/hexo/interrupt.h

     
    189189#endif
    190190}
    191191
     192#define CPU_EXCEPTION_ILLEGAL_INS  0x1
     193#define CPU_EXCEPTION_DATA_ERROR   0x2
     194#define CPU_EXCEPTION_INS_ERROR    0x3
     195#define CPU_EXCEPTION_DATA_ALIGN   0x4
     196
    192197#endif
    193198
  • cpu/arm/arm.config

     
    8383# provide CONFIG_CPU_ARM_T_PROFILE
    8484provide CONFIG_CPU_ARM_FPU=soft
    8585%config end
     86
     87%config CONFIG_CPU_ARM_CUSTOM_IRQ_HANDLER
     88desc Has custom ICU-based IRQ handler, often seen in microcontrollers
     89parent CONFIG_CPU_ARM
     90%config end
  • cpu/arm/boot.c

     
    2020
    2121*/
    2222
     23#include <hexo/asm.h>
     24
    2325#ifdef CONFIG_SOCLIB_MEMCHECK
    2426# include <arch/mem_checker.h>
    2527#endif
    2628
     29#define GET_OP2REL(name, rd, rt, op2)                                  \
     30    "ldr  " rd ", =" name "             \n\t"                          \
     31    "mrc p15,0," rt ",c13,c0," #op2 "   \n\t"                          \
     32    "ldr  " rd ", [" rd ", +" rt "]     \n\t"
     33#define GET_ABS(name, rd)                                              \
     34    "ldr  " rd ", =" name "     \n\t"                                  \
     35    "ldr  " rd ", [" rd "]      \n\t"
     36
    2737#ifdef CONFIG_SMP
    28 # define GET_HANDLER_ADDRESS(name, rd, rt, op2)                                            \
    29         "ldr  " rd ", =" name "             \n\t"                                                  \
    30         "mrc p15,0," rt ",c13,c0," #op2 "   \n\t"                                                  \
    31         "ldr  " rd ", [" rd ", +" rt "]     \n\t"
     38# define CPULOCAL_GET(name, rd, rt) GET_OP2REL(name, rd, rt, 3)
    3239#else
    33 # define GET_HANDLER_ADDRESS(name, rd, rt, foo)                                            \
    34         "ldr  " rd ", =" name "     \n\t"                                                                  \
    35         "ldr  " rd ", [" rd "]      \n\t"
     40# define CPULOCAL_GET(name, rd, rt) GET_ABS(name, rd)
    3641#endif
    3742
    38 # define GET_CPULOCAL_HANDLER_ADDRESS(name, rd, rt) GET_HANDLER_ADDRESS(name, rd, rt, 3)
    39 # define GET_CONTEXTLOCAL_HANDLER_ADDRESS(name, rd, rt) GET_HANDLER_ADDRESS(name, rd, rt, 4)
     43#define CONTEXTLOCAL_GET(name, rd, rt) GET_OP2REL(name, rd, rt, 4)
    4044
    4145
    4246asm(
    43     ".section        .boot,\"ax\"                       \n"
     47    ".section        .boot,\"ax\"           \n"
    4448
    45     ".globl cpu_boot                            \n\t"
    46         ".func cpu_boot                             \n\t"
    47         ".type   cpu_boot, %function \n\t"
    48         "cpu_boot:                   \n\t"
    49         "b arm_boot                     \n\t"
    50         "b arm_exc_undef                \n\t"
    51         "b arm_exc_swi                  \n\t"
    52         "b arm_exc_pabt                 \n\t"
    53         "b arm_exc_dabt                 \n\t"
    54         "nop                            \n\t"
    55         "b arm_exc_irq                  \n\t"
    56         // We dont like FIQ. Therefore, we'll return straight.
    57         "subs pc, r14, #4               \n\t"
    58         ".size   cpu_boot, .-cpu_boot\n\t"
    59         ".endfunc \n\t"
     49    FUNC_START(cpu_boot)
     50    "cpu_boot:                   \n\t"
     51    "b arm_boot                  \n\t"
     52    "ldr pc, =arm_exc_undef      \n\t"
     53    "ldr pc, =arm_exc_swi        \n\t"
     54    "ldr pc, =arm_exc_pabt       \n\t"
     55    "ldr pc, =arm_exc_dabt       \n\t"
     56    "nop                         \n\t"
     57#if defined(CONFIG_CPU_ARM_CUSTOM_IRQ_HANDLER)
     58    "ldr pc, =arm_c_irq_handler  \n\t"
     59    "ldr pc, =arm_c_fiq_handler  \n\t"
     60#else
     61    "ldr pc, =arm_exc_irq        \n\t"
     62    "ldr pc, =arm_exc_fiq        \n\t"
     63#endif
     64    FUNC_END(cpu_boot)
    6065
    61     ".globl arm_boot                            \n\t"
    62         ".func arm_boot                             \n\t"
    63         ".type   arm_boot, %function   \n\t"
    64         "arm_boot:                     \n\t"
    65         "mrc  p15,0,r4,c0,c0,5       \n\t"
     66    FUNC_START(arm_boot)
     67#if !defined(CONFIG_ARCH_SIMPLE)
     68    "mrc  p15,0,r4,c0,c0,5       \n\t"
    6669# ifndef CONFIG_SMP
    67     "cmp        r4,     #0                      \n\t"
    68     "1: bne     1b                              \n\t"
     70    "cmp    r4, #0              \n\t"
     71    "1: bne 1b                  \n\t"
    6972# endif
    7073
    71         // Allocate 1K stacks
    72         "lsl  r5, r4, #10            \n\t"
     74    // Allocate 1K stacks
     75    "lsl  r5, r4, #10            \n\t"
    7376
    7477    "ldr  r13, =__initial_stack-16   \n\t"
    75         "subs r13, r13, r5                         \n\t"
    76 
    77 #ifdef CONFIG_SOCLIB_MEMCHECK
     78    "subs r13, r13, r5                         \n\t"
     79# ifdef CONFIG_SOCLIB_MEMCHECK
    7880    "mov  r0, #1024           \n\t"
    7981    "ldr  r2, =" ASM_STR(SOCLIB_MC_MAGIC_VAL) "  \n\t"
    8082    "ldr  r1, =" ASM_STR(CONFIG_SOCLIB_MEMCHECK_ADDRESS) " \n\t"
    8183    "str  r2, [r1, #(" ASM_STR(SOCLIB_MC_MAGIC) "-" ASM_STR(CONFIG_SOCLIB_MEMCHECK_ADDRESS) ")] \n\t"
    8284    "str  r0, [r1, #(" ASM_STR(SOCLIB_MC_R2) "-" ASM_STR(CONFIG_SOCLIB_MEMCHECK_ADDRESS) ")] \n\t"
    83         "sub  r0, sp, r0   \n\t"
    84         "add  r0, r0, #4   \n\t"
     85    "sub  r0, sp, r0   \n\t"
     86    "add  r0, r0, #4   \n\t"
    8587    "str  r0, [r1, #(" ASM_STR(SOCLIB_MC_R1) "-" ASM_STR(CONFIG_SOCLIB_MEMCHECK_ADDRESS) ")] \n\t"
    8688    "str  r4, [r1, #(" ASM_STR(SOCLIB_MC_CTX_CREATE) "-" ASM_STR(CONFIG_SOCLIB_MEMCHECK_ADDRESS) ")] \n\t"
    8789    "str  r4, [r1, #(" ASM_STR(SOCLIB_MC_CTX_SET) "-" ASM_STR(CONFIG_SOCLIB_MEMCHECK_ADDRESS) ")] \n\t"
     
    9193
    9294    "mov  r0, #0             \n\t"
    9395    "str  r0, [r1, #(" ASM_STR(SOCLIB_MC_MAGIC) "-" ASM_STR(CONFIG_SOCLIB_MEMCHECK_ADDRESS) ")] \n\t"
     96# endif /* CONFIG_SOCLIB_MEMCHECK */
     97#else /* is ARCH_SIMPLE*/
     98    "ldr  r13, =__initial_stack-16  \n\t"
    9499#endif
    95100
    96101    /* Get the device tree and put it in first arg */
     
    102107    /* Put a 0 in second arg */
    103108    "mov  r1, #0                      \n\t"
    104109
    105         "ldr  r12, =arch_init             \n\t"
    106         "bx   r12                         \n\t"
    107         ".size   arm_boot, .-arm_boot     \n\t"
    108         ".endfunc \n\t"
     110    "ldr  r12, =arch_init             \n\t"
     111    "bx   r12                         \n\t"
     112    FUNC_END(arm_boot)
    109113
    110         ".globl arm_hw_interrupt_proxy    \n\t"
    111         ".type   arm_hw_interrupt_proxy, %function   \n\t"
    112         "arm_hw_interrupt_proxy:          \n\t"
    113         "push {r0, r1, r2, r3, r12, lr}   \n\t"
    114         "mov  r0, #0                      \n\t"
    115         GET_CPULOCAL_HANDLER_ADDRESS("cpu_interrupt_handler", "r12", "r1")
    116         "mov  lr, pc                      \n\t"
    117         "bx   r12                         \n\t"
    118         "pop  {r0, r1, r2, r3, r12, pc}   \n\t"
    119         ".size   arm_hw_interrupt_proxy, .-arm_hw_interrupt_proxy     \n\t"
     114    );
    120115
    121         /* Exception handler, from switching code below, desc struct is in r0 (to restore) */
    122         ".globl arm_ex_interrupt_proxy    \n\t"
    123         ".type   arm_ex_interrupt_proxy, %function   \n\t"
    124         "arm_ex_interrupt_proxy:          \n\t"
    125         "push  {r1, r2, r3, r4, r12, lr}  \n\t"
    126         /* Leave room for r15 */
    127         "sub   sp, sp, #12                 \n\t"
    128         /* Get user's sp & lr and put them in table */
    129         "stmia r1, {r13, r14}^             \n\t"
    130         /* All those are directly from user. */
    131         "push  {r1, r2, r3, r4, r5, r6, r7, r8, r9, r10, r11, r12} \n\t"
    132         /* Get back user's r0 and put it in table */
    133         "ldr   r1, [r0, #8]                \n\t"
    134         "push  {r1}                        \n\t"
    135         /* Regtable is in *sp */
    136         "mov   a4, sp                      \n\t"
    137         /* Get user's r13 as stack pointer */
    138         "ldr   a1, [r1, #4*13]             \n\t"
    139         /* Push it as 5th argument */
    140         "push  {a1}                        \n\t"
    141         /* data pointer */
    142         "mrc p15, 0, a3, c6, c0, 0         \n\t"
    143         /* TODO: PC */
    144         "mrc p15, 0, a2, c6, c0, 2         \n\t"
    145         /* TODO: type */
    146         "mov   a1, #0                      \n\t"
    147         GET_CPULOCAL_HANDLER_ADDRESS("cpu_interrupt_handler", "r12", "r1")
    148         "mov  lr, pc                      \n\t"
    149         "bx   r12                         \n\t"
    150         /* 1 level for r5 and 15 levels for reg table (not 16) */
    151         "add  sp, #16*4                   \n\t"
    152         "pop  {r1, r2, r3, r4, r12, pc}   \n\t"
    153         ".size   arm_ex_interrupt_proxy, .-arm_ex_interrupt_proxy     \n\t"
    154 
    155 
    156         /* Syscall handler, directly in Super32 */
    157         ".globl arm_exc_swi                    \n\t"
    158         ".type   arm_exc_swi, %function        \n\t"
    159         "arm_exc_swi:                          \n\t"
    160         "push {r0, r1, r2, r3, r4, r5, r6, r7, r8, r9, r10, r11, r12, lr}  \n\t"
    161         "ldr  r0, [lr], #-4                \n\t"
    162         "and  r0, #0x00ffffff              \n\t"
    163         "mov  r1, sp                       \n\t"
    164         GET_CONTEXTLOCAL_HANDLER_ADDRESS("cpu_syscall_handler", "r12", "r1")
    165         "mov  lr, pc                      \n\t"
    166         "bx   r12                         \n\t"
    167         "pop  {r0, r1, r2, r3, r4, r5, r6, r7, r8, r9, r10, r11, r12, lr}  \n\t"
    168         "movs pc, r14                     \n\t"
    169         ".size   arm_exc_swi, .-arm_exc_swi     \n\t"
    170 
    171         /* Other handlers, in other modes to Super32 */
    172 #define IMPLEMENT_EXC(exc_name, handler, ret_subs_offset, mode)            \
    173     ".globl arm_" exc_name "           \n\t"                                               \
    174         ".type   arm_" exc_name ", %function  \n\t"                                                \
    175     "arm_" exc_name ":                 \n\t"                                               \
    176         /* save user's r0 */                                                                                       \
    177     "str    r0, [sp, #8]               \n\t"                                               \
    178         /* save user's pc */                                                                                       \
    179     "str    lr, [sp]                   \n\t"                                               \
    180         /* save user's cpsr from current spsr */                                                   \
    181         "mrs    r0, spsr                   \n\t"                                                   \
    182     "str    r0, [sp, #4]               \n\t"                                               \
    183         /* pass struct pointer to super32 */                                                       \
    184     "mov    r0, sp                     \n\t"                                               \
    185         /* switch to super32 */                                                                                    \
    186         "mrs    lr, cpsr                   \n\t"                                                   \
    187         "bic    lr, lr, #0x1f              \n\t"                                                   \
    188         "orr    lr, lr, #0x13              \n\t"                                                   \
    189         "msr    cpsr, lr                   \n\t"                                                   \
    190         "push   {lr}                       \n\t"                                                   \
    191     handler " \n\t"                                                                                                        \
    192         "pop    {lr}                       \n\t"                                                   \
    193         /* switch back to mode we are from */                                                      \
    194         "mrs    r0, cpsr                   \n\t"                                                   \
    195         "bic    r0, r0, #0x1f              \n\t"                                                   \
    196         "orr    r0, r0, #" #mode "         \n\t"                                                   \
    197         "msr    cpsr, r0                   \n\t"                                                   \
    198         /* restore user's cpsr to current spsr */                                                  \
    199     "ldr    r0, [sp, #4]               \n\t"                                               \
    200         "msr    spsr, r0                   \n\t"                                                   \
    201         /* restore user's pc */                                                                                    \
    202     "ldr    lr, [sp]                   \n\t"                                               \
    203         /* restore r0 */                                                                                                   \
    204     "ldr    r0, [sp, #8]               \n\t"                                               \
    205         "subs   pc, lr, #" #ret_subs_offset "\n\t"                                                 \
    206         ".size   arm_" exc_name ", .-arm_" exc_name "     \n\t"
    207 
    208         IMPLEMENT_EXC("exc_undef", "bl arm_ex_interrupt_proxy", 0, 0x1b)
    209         IMPLEMENT_EXC("exc_pabt", "bl arm_ex_interrupt_proxy", 4, 0x17)
    210         IMPLEMENT_EXC("exc_dabt", "bl arm_ex_interrupt_proxy", 8, 0x17)
    211         IMPLEMENT_EXC(
    212                 "exc_irq",
    213                 "push {r1, r2, r3, r12}   \n\t"
    214                 GET_CPULOCAL_HANDLER_ADDRESS("cpu_interrupt_handler_arg", "r0", "r1")
    215                 GET_CPULOCAL_HANDLER_ADDRESS("cpu_interrupt_handler", "r2", "r1")
    216                 "mov  r1, #0                      \n\t"
    217                 "mov  lr, pc                      \n\t"
    218                 "bx   r2                         \n\t"
    219                 "pop  {r1, r2, r3, r12}   \n\t",
    220                 4, 0x12)
    221 
    222         );
     116// Local Variables:
     117// tab-width: 4;
     118// c-basic-offset: 4;
     119// indent-tabs-mode: nil;
     120// End:
     121//
     122// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=4:softtabstop=4
  • cpu/arm/cpu_init.c

     
    3131# include <arch/mem_checker.h>
    3232#endif
    3333
    34 #ifndef CONFIG_DRIVER_ICU_ARM
     34#ifdef CONFIG_CPU_ARM_CUSTOM_IRQ_HANDLER
    3535static uint32_t arm_irq_stack[128/4];
    3636#endif
    3737
    3838CPU_LOCAL cpu_exception_handler_t  *cpu_exception_handler;
    3939
    4040struct arm_exception_context_s {
    41         uint32_t user_pc;
    42         uint32_t user_cpsr;
    43         uint32_t user_r0;
     41        uint32_t r0;
     42        uint32_t r1;
     43        uint32_t pc;
     44        uint32_t cpsr;
    4445};
    4546
    4647#ifdef CONFIG_SMP
     
    7778#endif
    7879
    7980        struct arm_exception_context_s *cpu_context = arm_exception_context[cpu_id()];
    80 #ifndef CONFIG_DRIVER_ICU_ARM
    81         arm_setup_exception_stack(arm_irq_stack+sizeof(arm_irq_stack)-4, 0x12);
     81#ifdef CONFIG_CPU_ARM_CUSTOM_IRQ_HANDLER
     82        arm_setup_exception_stack(arm_irq_stack+sizeof(arm_irq_stack)/4-4, 0x12);
    8283#else
    8384        arm_setup_exception_stack(&cpu_context[0], 0x12); // IRQ
    8485#endif
  • cpu/arm/Makefile

     
    44cpu_context.o
    55
    66ifeq ($(CONFIG_CPU_RESET_HANDLER),defined)
    7 ifeq ($(CONFIG_CPU_ARM_M_PROFILE),defined)
    8 objs += boot_m.o
    9 else
    10 objs += boot.o
     7objs += boot.o exception.o
    118endif
    12 endif
    139
    1410copy = ldscript
    1511
  • cpu/ppc/exception.c

     
    1515    along with MutekH; if not, write to the Free Software Foundation,
    1616    Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
    1717
    18     Copyright (c) Nicolas Pouillon <nipo@ssji.net>, 2009
    19 
     18    Copyright (c) 2009-2010, Nicolas Pouillon <nipo@ssji.net>
    2019*/
    2120
     21#include <hexo/asm.h>
     22#include <hexo/interrupt.h>
     23
     24#define GET_SPRREL(name, rd, rt, spr)                                  \
     25    "mfspr " #rt ", " #spr "             \n\t"                         \
     26    "lwz   " #rd ", " name "(" #rt ")    \n\t"
     27#define GET_ABS(name, rd, rt)                                          \
     28    "lis   " #rt ", " name "@ha           \n\t"                        \
     29    "lwz   " #rd ", " name "@l(" #rt ")   \n\t"
     30#define LA(rd, name)                                                    \
     31    "lis   " #rd ", (" #name ")@h         \n\t"                        \
     32    "ori   " #rd ", " #rd ", (" #name ")@l\n\t"
     33
     34#ifdef CONFIG_SMP
     35# define CPULOCAL_GET(name, rd, rt) GET_SPRREL(name, rd, rt, 0x105)
     36#else
     37# define CPULOCAL_GET(name, rd, rt) GET_ABS(name, rd, rt)
     38#endif
     39
     40#define CONTEXTLOCAL_GET(name, rd, rt) GET_SPRREL(name, rd, rt, 0x104)
     41
     42
     43#define SPRG0 "0x110"
     44#define SPRG1 "0x111"
     45
     46#define DO_REG_2_3(op, n, off)                                  \
     47    #op "   2, " #off "+4* 0(" #n ")      \n\t"                 \
     48    #op "   3, " #off "+4* 1(" #n ")      \n\t"
     49
     50#define DO_REG_4_12(op, n, off)                                 \
     51    #op "   4, " #off "+4* 0(" #n ")      \n\t"                 \
     52    #op "   5, " #off "+4* 1(" #n ")      \n\t"                 \
     53    #op "   6, " #off "+4* 2(" #n ")      \n\t"                 \
     54    #op "   7, " #off "+4* 3(" #n ")      \n\t"                 \
     55    #op "   8, " #off "+4* 4(" #n ")      \n\t"                 \
     56    #op "   9, " #off "+4* 5(" #n ")      \n\t"                 \
     57    #op "  10, " #off "+4* 6(" #n ")      \n\t"                 \
     58    #op "  11, " #off "+4* 7(" #n ")      \n\t"                 \
     59    #op "  12, " #off "+4* 8(" #n ")      \n\t"
     60
     61#define DO_REG_2_12(op, n, off)                                        \
     62    DO_REG_2_3(op, n, off)                                             \
     63    DO_REG_4_12(op, n, off+8)
     64
     65
    2266/*
    23         ".section      \".ppc_special." #name "\",\"ax\",@progbits                      \n\t"
    24     ".globl ppc_special_" #name "_entry                         \n\t"
    25         ".type  ppc_special_" #name "_entry, @function   \n"
    26     "ppc_special_" #name "_entry:                                       \n\t"
    27     "stwu 1, -16(1)                                     \n\t"
    28     "stw 0, 8(1)                                        \n\t"
    29     "mflr 0                                     \n\t"
    30     "stw 0, 12(1)                                       \n\t"
    31         "bl " #func "\n\t"
    32     "lwz 0, 12(1)                                       \n\t"
    33     "mtlr 0                                     \n\t"
    34     "lwz 0, 8(1)                                        \n\t"
    35     "addi 1, 1, 16                                      \n\t"
    36         #ret_ins "\n\t"
    37         ".size ppc_special_" #name "_entry, .-ppc_special_" #name "_entry \n\t"
    38 */
     67  (cls / tls are r/o for user, no need to restore)
    3968
    40 #define SAVE_REG_2_12(n, off)                                                                   \
    41     "stw   2, " #off "+4* 0(" #n ")      \n\t"                                  \
    42     "stw   3, " #off "+4* 1(" #n ")      \n\t"                                  \
    43     "stw   4, " #off "+4* 2(" #n ")      \n\t"                                  \
    44     "stw   5, " #off "+4* 3(" #n ")      \n\t"                                  \
    45     "stw   6, " #off "+4* 4(" #n ")      \n\t"                                  \
    46     "stw   7, " #off "+4* 5(" #n ")      \n\t"                                  \
    47     "stw   8, " #off "+4* 6(" #n ")      \n\t"                                  \
    48     "stw   9, " #off "+4* 7(" #n ")      \n\t"                                  \
    49     "stw  10, " #off "+4* 8(" #n ")      \n\t"                                  \
    50     "stw  11, " #off "+4* 9(" #n ")      \n\t"                                  \
    51     "stw  12, " #off "+4*10(" #n ")      \n\t"
     69  Whatever the exception, we need to:
     70  * copy r0, r1 -> sprg0, sprg1
     71  * save cr to r0
     72  * get cpu "previous" mode
     73  * if from kernel
     74    * copy back r1 from sprg1
     75  * if from user
     76    * get task's kernel stack to r1
     77  * reserve 32+5 registers
     78  * put cr (r0)
     79  * put exception type in r0
     80  * put srr0/2 (PC), srr1/3 (msr)
    5281
    53 #define RESTORE_REG_2_12(n, off)                                                                \
    54     "lwz   2, " #off "+4* 0(" #n ")      \n\t"                                  \
    55     "lwz   3, " #off "+4* 1(" #n ")      \n\t"                                  \
    56     "lwz   4, " #off "+4* 2(" #n ")      \n\t"                                  \
    57     "lwz   5, " #off "+4* 3(" #n ")      \n\t"                                  \
    58     "lwz   6, " #off "+4* 4(" #n ")      \n\t"                                  \
    59     "lwz   7, " #off "+4* 5(" #n ")      \n\t"                                  \
    60     "lwz   8, " #off "+4* 6(" #n ")      \n\t"                                  \
    61     "lwz   9, " #off "+4* 7(" #n ")      \n\t"                                  \
    62     "lwz  10, " #off "+4* 8(" #n ")      \n\t"                                  \
    63     "lwz  11, " #off "+4* 9(" #n ")      \n\t"                                  \
    64     "lwz  12, " #off "+4*10(" #n ")      \n\t"
     82  Generic part:
     83  * put ctr, lr
     84  * put sprg[01] on stack
     85  * put gpr 2-12 on stack
     86  * (put gpr 13-31 on stack)
     87  * handle exception
     88  * restore ctr, cr, lr, srr0 (PC), srr1 (msr)
     89  * (restore gpr 13-31)
     90  * restore gpr 2-12
     91  * load r0 from *sp
     92  * load sp from *sp
     93  * rfi
    6594
    66 #ifdef CONFIG_SMP
    67 # define GET_HANDLER_ADDRESS(name, rd, rt, spr)                                            \
    68         "mfspr " #rt ", " #spr "                \n\t"                                      \
    69     "lwz   " #rd ", " name "(" #rt ")    \n\t"
     95  stack layout:
     96   0     1    2    3    4         5          6      37
     97  [sp] [ctr] [lr] [cr] [srr0/pc] [srr1/msr] [r0 .. r31]
     98 */
     99
     100#if defined(CONFIG_USER_MODE)
     101# define GET_STACK_SAVE_CR                                             \
     102    /* put msr in cr and do bit test (user mode) */                    \
     103    "mf" #msr_srr " 1                     \n\t"                        \
     104    "mtcr   1                             \n\t"                        \
     105    "bt     17, 1f                        \n\t"                        \
     106    /* from kernel */                                                  \
     107    "mfspr 1, " SPRG1 "                   \n\t"                        \
     108    "stwu  1, -38*4(1)                    \n\t"                        \
     109    "stw   0,  3 *4(1)                    \n\t"                        \
     110    "b 2f                                 \n\t"                        \
     111    "1:                                   \n\t"                        \
     112    CONTEXTLOCAL_GET("context_kstack", 1, 1)                           \
     113    "addi  1, -38*4(1)                    \n\t"                        \
     114    /* save cr */                                                      \
     115    "stw   0,  3 *4(1)                    \n\t"                        \
     116    /* save old sp */                                                  \
     117    "mfspr 0,  " SPRG1 "                  \n\t"                        \
     118    "stw   0,  0 *4(1)                    \n\t"                        \
     119    "2:                                   \n\t"
    70120#else
    71 # define GET_HANDLER_ADDRESS(name, rd, rt, foo)                                            \
    72     "lis   " #rt ", " name "@ha           \n\t"                                            \
    73     "lwz   " #rd ", " name "@l(" #rt ")     \n\t"
     121# define GET_STACK_SAVE_CR                                             \
     122    "stwu  1, -38*4(1)                    \n\t"                        \
     123    /* save cr */                                                      \
     124    "stw   0,  3 *4(1)                    \n\t"
    74125#endif
    75126
    76 # define GET_CPULOCAL_HANDLER_ADDRESS(name, rd, rt) GET_HANDLER_ADDRESS(name, rd, rt, 0x105)
    77 # define GET_CONTEXTLOCAL_HANDLER_ADDRESS(name, rd, rt) GET_HANDLER_ADDRESS(name, rd, rt, 0x104)
     127#define prepare_exception(pc_srr, msr_srr)                             \
     128    "mtspr  " SPRG0 ", 0                  \n\t"                        \
     129    "mtspr  " SPRG1 ", 1                  \n\t"                        \
     130    "mfcr   0                             \n\t"                        \
     131    GET_STACK_SAVE_CR                                                  \
     132    /* pc */                                                           \
     133    "mf" #pc_srr " 0                      \n\t"                        \
     134    "stw    0, 4 *4(1)                    \n\t"                        \
     135    /* srr1 */                                                         \
     136    "mf" #msr_srr " 0                     \n\t"                        \
     137    "stw    0, 5 *4(1)                    \n\t"                        \
     138    /* ctr */                                                          \
     139    "mfctr 0                              \n\t"                        \
     140    "stw   0, 1 *4(1)                     \n\t"
    78141
    79 #define HANDLE_EXCEPTION(eno, srr02)                                                               \
    80         /* r1 -> @0 */                                                                                                     \
    81     "stwu  1,-4*22(1)                      \n\t"                                           \
    82         /* r0 -> @3 */                                                                                                     \
    83     "stw   0, 4* 7(1)                      \n\t"                                           \
    84         /* lr -> @19 */                                                                                                    \
    85     "mflr  0                               \n\t"                                           \
    86     "stw   0, 4*19(1)                      \n\t"                                           \
    87         /* cr -> @21 */                                                                                                    \
    88     "mfcr  0                               \n\t"                                           \
    89     "stw   0, 4*21(1)                      \n\t"                                           \
    90         /* r2-r12 -> @8-18 */                                                                                      \
    91         SAVE_REG_2_12(1, 32)                                                                                       \
    92                                                                                                                                            \
    93         /* ctr -> @20 */                                                                                                   \
    94         "mfctr 0                               \n\t"                                       \
    95     "stw   0, 4*20(1)                      \n\t"                                           \
    96                                                                                                                                            \
    97         GET_CPULOCAL_HANDLER_ADDRESS("cpu_exception_handler", 0, 3)                \
    98         "mtctr 0                               \n\t"                                       \
    99                                                                                                                                            \
    100         /* Put handler arguments: */                                                                       \
    101         /* a0: type */                                                                                                     \
    102         /* a1: execptr (srr) */                                                                                    \
    103         /* a2: dataptr (dear) */                                                                                   \
    104         /* a3: regtable (sp + 7*4) */                                                                      \
    105         /* a4: sp (sp + 22*4) */                                                                                   \
    106         "li    3, " #eno "                     \n\t"                                       \
    107         "mfsrr" #srr02 " 4                     \n\t"                                       \
    108         "mfspr  5, 981                         \n\t"                                       \
    109         "addi   6, 1, 4* 7                     \n\t"                                       \
    110         "addi   7, 1, 4*22                     \n\t"                                       \
    111                                                                                                                                            \
    112         "bctrl                                 \n\t"                                       \
    113                                                                                                                                            \
    114         /* ctr -> @20 */                                                                                                   \
    115     "lwz   0, 4*20(1)                      \n\t"                                           \
    116         "mtctr 0                               \n\t"                                       \
    117                                                                                                                                            \
    118         /* r2-r12 -> @8-18 */                                                                                      \
    119         RESTORE_REG_2_12(1, 32)                                                                                    \
    120                                                                                                                                            \
    121         /* lr -> @19 */                                                                                                    \
    122     "lwz   0, 4*19(1)                      \n\t"                                           \
    123     "mtlr  0                               \n\t"                                           \
    124                                                                                                                                            \
    125         /* cr -> @21 */                                                                                                    \
    126     "lwz   0, 4*21(1)                      \n\t"                                           \
    127     "mtcr  0                               \n\t"                                           \
    128                                                                                                                                            \
    129         /* r0 -> @7 */                                                                                                     \
    130     "lwz  0, 4* 7(1)                         \n\t"                                         \
    131         /* r1 -> @0 */                                                                                                     \
    132     "addi 1, 1, 4*18                      \n\t"
     142#define handle_exception(name)                                         \
     143    LA(0, exception_common)                                            \
     144    "mtctr 0                              \n\t"                        \
     145    /* exc type */                                                     \
     146    "li    0, " ASM_STR(name) "           \n\t"                        \
     147    "bctr                                 \n\t"
    133148
    134 asm(
    135     ".section        .excep,\"ax\",@progbits            \n"
     149#define CRASH(x, y)                                                    \
     150    prepare_exception(x, y)                                            \
     151    handle_exception(CPU_EXCEPTION_OTHER)
    136152
    137         /* critical interrupt (critical, async) */
    138         ".org 0x100\n"
     153#define handle_interrupt(no)                                           \
     154    LA(0, interrupt_common)                                            \
     155    "mtctr 0                              \n\t"                        \
     156    "li    0, " #no "                     \n\t"                        \
     157    "bctr                                 \n\t"
    139158
    140         /* machine check (critical, async, imprecise) */
    141         ".org 0x200\n"
    142     ".globl ppc_special_machine_check_entry                   \n\t"
    143         ".type  ppc_special_machine_check_entry, @function  \n"
    144     "ppc_special_machine_check_entry:                 \n\t"
    145         HANDLE_EXCEPTION(3, 2)
    146         "rfci                                  \n\t"
    147         ".size ppc_special_machine_check_entry, .-ppc_special_machine_check_entry \n\t"
     159#define handle_syscall()                                               \
     160    LA(0, syscall_common)                                              \
     161    "mtctr 0                              \n\t"
    148162
    149         /* data storage */
    150         ".org 0x300\n"
    151     ".globl ppc_special_data_storage_entry                    \n\t"
    152         ".type  ppc_special_data_storage_entry, @function  \n"
    153     "ppc_special_data_storage_entry:                  \n\t"
    154         HANDLE_EXCEPTION(4, 0)
    155         "rfi                                  \n\t"
    156         ".size ppc_special_data_storage_entry, .-ppc_special_data_storage_entry \n\t"
     163asm(".section        .text,\"ax\",@progbits  \n"
    157164
    158         /* instr storage */
    159         ".org 0x400\n"
    160     ".globl ppc_special_instr_storage_entry                   \n\t"
    161         ".type  ppc_special_instr_storage_entry, @function  \n"
    162     "ppc_special_instr_storage_entry:                 \n\t"
    163         HANDLE_EXCEPTION(5, 0)
    164         "rfi                                  \n\t"
    165         ".size ppc_special_instr_storage_entry, .-ppc_special_instr_storage_entry \n\t"
     165    FUNC_START(exception_common)
     166    DO_REG_2_12(stw, 1, 8*4)
     167    /* lr */
     168    "mflr  3                              \n\t"
     169    "stw   3, 2 *4(1)                     \n\t"
     170    /* r0 */
     171    "mfspr 3, " SPRG0 "                   \n\t"
     172    "stw   3, 6 *4(1)                     \n\t"
     173    /* r1 */
     174    "mfspr 3, " SPRG1 "                   \n\t"
     175    "stw   3, 7 *4(1)                     \n\t"
     176    /* Put handler arguments: */
     177    /* a0: type */
     178    /* a1: execptr (srr) */
     179    /* a2: dataptr (dear) */
     180    /* a3: regtable (sp + 6*4) */
     181    /* a4: sp (sp + 22*4) */
     182    "or    3, 0, 0                        \n\t"
     183    "lwz   4, 4 *4(1)                     \n\t"
     184    "addi  6, 1, 6*4                      \n\t"
     185    "lwz   7, 7 *4(1)                     \n\t"
    166186
    167         /* external (async) */
    168         ".org 0x500\n"
    169     ".globl ppc_special_external_entry                \n\t"
    170         ".type  ppc_special_external_entry, @function  \n"
    171     "ppc_special_external_entry:           \n\t"
    172         /* r1 -> @0 */
    173     "stwu  1,-4*18(1)                      \n\t"
    174         /* r0 -> @3 */
    175     "stw   0, 4* 3(1)                      \n\t"
    176         /* lr -> @15 */
    177     "mflr  0                               \n\t"
    178     "stw   0, 4*15(1)                      \n\t"
    179         /* cr -> @17 */
    180     "mfcr  0                               \n\t"
    181     "stw   0, 4*17(1)                      \n\t"
    182         /* r2-r12 -> @4-14 */
    183         SAVE_REG_2_12(1, 16)
     187    /*
     188     * dont use 0 as 3rd arg, or you'll get crappy things,
     189     * hijack r5 and do mfdear afterwards
     190     */
     191    CPULOCAL_GET("cpu_exception_handler", 0, 5)
     192    "mtctr 0                               \n\t"
     193    "mfdear 5                              \n\t"
    184194
    185         /* ctr -> @16 */
    186         "mfctr 0                               \n\t"
    187     "stw   0, 4*16(1)                      \n\t"
     195    /* Call the exception handler */
     196    "bctrl                                 \n\t"
     197    "b back_from_exception                 \n\t"
     198    FUNC_END(exception_common)
    188199
    189         GET_CPULOCAL_HANDLER_ADDRESS("cpu_interrupt_handler", 0, 3)
    190         "mtctr 0                               \n\t"
    191200
    192         GET_CPULOCAL_HANDLER_ADDRESS("cpu_interrupt_handler_arg", 3, 3)
    193201
    194         /* interrupt line is 0 */
    195         "li    4, 0                            \n\t"
     202    FUNC_START(interrupt_common)
     203    DO_REG_2_12(stw, 1, 8*4)
     204    /* lr */
     205    "mflr  3                              \n\t"
     206    "stw   3, 2 *4(1)                     \n\t"
     207    /* r0 */
     208    "mfspr 3, " SPRG0 "                   \n\t"
     209    "stw   3, 6 *4(1)                     \n\t"
     210    /* r1 */
     211    "mfspr 3, " SPRG1 "                   \n\t"
     212    "stw   3, 7 *4(1)                     \n\t"
     213    /* Put handler arguments: */
     214    /* a0: priv */
     215    /* a1: irq */
    196216
    197         "bctrl                                 \n\t"
     217    CPULOCAL_GET("cpu_interrupt_handler", 5, 5)
     218    CPULOCAL_GET("cpu_interrupt_handler_arg", 3, 3)
     219    "or    4, 0, 0                         \n\t"
     220    "mtctr 5                               \n\t"
    198221
    199         /* ctr -> @16 */
    200     "lwz   0, 4*16(1)                      \n\t"
    201         "mtctr 0                               \n\t"
     222    /* Call the interrupt handler */
     223    "bctrl                                 \n\t"
     224    "b back_from_exception                 \n\t"
     225    FUNC_END(interrupt_common)
    202226
    203         /* r2-r12 -> @4-14 */
    204         RESTORE_REG_2_12(1, 16)
    205227
    206         /* lr -> @15 */
    207     "lwz   0, 4*15(1)                      \n\t"
    208     "mtlr  0                               \n\t"
    209228
    210         /* cr -> @17 */
    211     "lwz   0, 4*17(1)                      \n\t"
    212     "mtcr  0                               \n\t"
     229    FUNC_START(syscall_common)
     230    DO_REG_2_12(stw, 1, 8*4)
     231    /* ctr */
     232    "mfctr 3                              \n\t"
     233    "stw   3, 1 *4(1)                     \n\t"
     234    /* lr */
     235    "mflr  3                              \n\t"
     236    "stw   3, 2 *4(1)                     \n\t"
     237    /* r0 */
     238    "mfspr 3, " SPRG0 "                   \n\t"
     239    "stw   3, 6 *4(1)                     \n\t"
     240    /* r1 */
     241    "mfspr 3, " SPRG1 "                   \n\t"
     242    "stw   3, 7 *4(1)                     \n\t"
     243    /* Put handler arguments: */
     244    /* a0: number */
     245    /* a1: regtable */
    213246
    214         /* r0 -> @3 */
    215     "lwz  0, 4* 3(1)                         \n\t"
    216         /* r1 -> @0 */
    217     "addi 1, 1, 4*18                      \n\t"
     247    CONTEXTLOCAL_GET("cpu_syscall_handler", 5, 5)
     248    "mtctr 5                              \n\t"
    218249
    219         "rfi                                  \n\t"
    220         ".size ppc_special_external_entry, .-ppc_special_external_entry \n\t"
     250    "li    3, 0                           \n\t"
     251    "addi  6, 1, 6*4                      \n\t"
    221252
     253    /* Call the syscall handler */
     254    "bctrl                                 \n\t"
     255    "b back_from_syscall                   \n\t"
     256    FUNC_END(syscall_common)
    222257
    223         /* alignment */
    224         ".org 0x600\n"
    225     ".globl ppc_special_alignment_entry               \n\t"
    226         ".type  ppc_special_alignment_entry, @function  \n"
    227     "ppc_special_alignment_entry:                     \n\t"
    228         HANDLE_EXCEPTION(2, 0)
    229         "rfi                                  \n\t"
    230         ".size ppc_special_alignment_entry, .-ppc_special_alignment_entry \n\t"
    231258
    232         /* program */
    233         ".org 0x700\n"
    234     ".globl ppc_special_program_entry                 \n\t"
    235         ".type  ppc_special_program_entry, @function  \n"
    236     "ppc_special_program_entry:               \n\t"
    237         HANDLE_EXCEPTION(1, 0)
    238         "rfi                                  \n\t"
    239         ".size ppc_special_program_entry, .-ppc_special_program_entry \n\t"
    240259
    241         /* fpu unusable */
    242         ".org 0x800\n"
    243260
    244         /* syscall */
    245         ".org 0xc00\n"
    246     ".globl ppc_special_syscall_entry                 \n\t"
    247         ".type  ppc_special_syscall_entry, @function  \n"
    248     "ppc_special_syscall_entry:           \n\t"
    249     "stwu 1, -4*15(1)                     \n\t"
    250     "stw   0, 4* 1(1)                      \n\t"
    251261
    252         SAVE_REG_2_12(1, 16)
     262    FUNC_START(back_from_exception)
     263    DO_REG_4_12(lwz, 1, 10*4)
    253264
    254     /* Put syscall number on first arg */
    255         "or    3, 0, 0                         \n\t"
    256     "mflr  0                               \n\t"
    257     "stw   0, 4*13(1)                      \n\t"
     265    /* Dont restore reg 4 to 12 for syscall return */
     266    "back_from_syscall:                   \n\t"
     267    DO_REG_2_3(lwz, 1, 8*4)
    258268
    259         "mfctr 0                               \n\t"
    260     "stw   0, 4*14(1)                      \n\t"
     269    /* ctr */
     270    "lwz   0, 1 *4(1)                     \n\t"
     271    "mtctr 0                              \n\t"
     272    /* lr */
     273    "lwz   0, 2 *4(1)                     \n\t"
     274    "mtlr  0                              \n\t"
     275    /* cr */
     276    "lwz    0,  3 *4(1)                   \n\t"
     277    "mtcr   0                             \n\t"
     278    /* srr0 */
     279    "lwz    0, 4 *4(1)                    \n\t"
     280    "mtsrr0 0                             \n\t"
     281    /* srr1 */
     282    "lwz    0, 5 *4(1)                    \n\t"
     283    "mtsrr1 0                             \n\t"
     284    /* r0 */
     285    "lwz   0, 6 *4(1)                     \n\t"
     286    /* r1 */
     287    "lwz   1, 7 *4(1)                     \n\t"
     288    "rfi                                  \n\t"
     289    FUNC_END(back_from_exception)
     290    );
    261291
    262         GET_CONTEXTLOCAL_HANDLER_ADDRESS("cpu_syscall_handler", 0, 3)
    263         "mtctr 0                               \n\t"
    264         "bctrl                                 \n\t"
    265292
    266     /* Put register table on second arg */
    267         /* Table is: sp, r0, r2, r3, ..., r12 */
    268         "or    4, 1, 1                         \n\t"
    269     "lwz   0, 4*14(1)                      \n\t"
    270         "mtctr 0                               \n\t"
    271293
    272     "lwz   0, 4*13(1)                      \n\t"
    273         RESTORE_REG_2_12(1, 16)
     294asm(
     295    ".section        .excep,\"ax\",@progbits        \n"
    274296
    275     "mtlr 0                               \n\t"
    276     "lwz  0, 4(1)                         \n\t"
    277     "lwz  1, 0(1)                         \n\t"
     297    /* critical interrupt (critical, async) */
     298    ".org 0x100\n"
     299    FUNC_START(ppc_critical_entry)
     300    prepare_exception(srr2, srr3)
     301    handle_interrupt(1)
     302    FUNC_END(ppc_critical_entry)
    278303
    279         "rfi                                  \n\t"
    280         ".size ppc_special_syscall_entry, .-ppc_special_syscall_entry \n\t"
     304    /* machine check (critical, async, imprecise) */
     305    ".org 0x200\n"
     306    FUNC_START(ppc_machine_entry)
     307    CRASH(srr2, srr3)
     308    FUNC_END(ppc_machine_entry)
    281309
    282         /* apu unavailable */
    283         ".org 0xf20\n"
     310    /* data storage */
     311    ".org 0x300\n"
     312    FUNC_START(ppc_data_storage_entry)
     313    prepare_exception(srr0, srr1)
     314    handle_exception(CPU_EXCEPTION_DATA_ERROR)
     315    FUNC_END(ppc_data_storage_entry)
    284316
    285         /* programmable-interval timer (async) */
    286         ".org 0x1000\n"
     317    /* instr storage */
     318    ".org 0x400\n"
     319    FUNC_START(ppc_instr_storage_entry)
     320    prepare_exception(srr0, srr1)
     321    handle_exception(CPU_EXCEPTION_INS_ERROR)
     322    FUNC_END(ppc_instr_storage_entry)
    287323
    288         /* fixed-interval timer (async) */
    289         ".org 0x1010\n"
     324    /* external (async) */
     325    ".org 0x500\n"
     326    FUNC_START(ppc_external_entry)
     327    prepare_exception(srr0, srr1)
     328    handle_interrupt(0)
     329    FUNC_END(ppc_external_entry)
    290330
    291         /* watchdog (critical, async) */
    292         ".org 0x1020\n"
    293331
    294         /* data tlb */
    295         ".org 0x1100\n"
     332    /* alignment */
     333    ".org 0x600\n"
     334    FUNC_START(ppc_align_entry)
     335    prepare_exception(srr0, srr1)
     336    handle_exception(CPU_EXCEPTION_DATA_ALIGN)
     337    FUNC_END(ppc_align_entry)
    296338
    297         /* ins tlb */
    298         ".org 0x1200\n"
     339    /* program */
     340    ".org 0x700\n"
     341    FUNC_START(ppc_program_entry)
     342    prepare_exception(srr0, srr1)
     343    handle_exception(CPU_EXCEPTION_ILLEGAL_INS)
     344    FUNC_END(ppc_program_entry)
    299345
    300         /* debug (critical, (a)sync) */
    301         ".org 0x2000\n"
     346    /* fpu unusable */
     347    ".org 0x800\n"
     348    FUNC_START(ppc_fpu_entry)
     349    CRASH(srr0, srr1)
     350    FUNC_END(ppc_fpu_entry)
    302351
     352    /* syscall */
     353    ".org 0xc00\n"
     354    FUNC_START(ppc_syscall_entry)
     355    handle_syscall()
     356    FUNC_END(ppc_syscall_entry)
     357
     358    /* apu unavailable */
     359    ".org 0xf20\n"
     360
     361    /* programmable-interval timer (async) */
     362    ".org 0x1000\n"
     363
     364    /* fixed-interval timer (async) */
     365    ".org 0x1010\n"
     366
     367    /* watchdog (critical, async) */
     368    ".org 0x1020\n"
     369
     370    /* data tlb */
     371    ".org 0x1100\n"
     372
     373    /* ins tlb */
     374    ".org 0x1200\n"
     375
     376    /* debug (critical, (a)sync) */
     377    ".org 0x2000\n"
     378
    303379    );
    304380
     381
     382// Local Variables:
     383// tab-width: 4;
     384// c-basic-offset: 4;
     385// indent-tabs-mode: nil;
     386// End:
     387//
     388// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=4:softtabstop=4
  • cpu/ppc/notes.rst

     
     1Special purpose register usage
     2------------------------------
     3
     4===== ====== ======================= ==========
     5reg   sprn   data                    attributes
     6===== ====== ======================= ==========
     7sprg0 0x110  exception handler r0    rw
     8----- ------ ----------------------- ----------
     9sprg1 0x111  exception handler r1    rw
     10----- ------ ----------------------- ----------
     11sprg2 0x112  exception handler r2    rw
     12----- ------ ----------------------- ----------
     13sprg4 0x104  task-local-storage base ro, user
     14----- ------ ----------------------- ----------
     15sprg4 0x114  task-local-storage base rw
     16----- ------ ----------------------- ----------
     17sprg5 0x105  cpu-local-storage base  ro, user
     18----- ------ ----------------------- ----------
     19sprg5 0x115  cpu-local-storage base  rw
     20----- ------ ----------------------- ----------
  • cpu/ppc/include/cpu/hexo/interrupt.h

     
    166166  //  __asm__ volatile ("");
    167167}
    168168
     169#define CPU_EXCEPTION_ILLEGAL_INS  0x1
     170#define CPU_EXCEPTION_DATA_ERROR   0x2
     171#define CPU_EXCEPTION_INS_ERROR    0x3
     172#define CPU_EXCEPTION_DATA_ALIGN   0x4
     173#define CPU_EXCEPTION_OTHER        0x5
     174
    169175#endif
    170176
  • cpu/ppc/include/cpu/hexo/cpu.h

     
    4444#define CPU_FAULT_NAMES {       \
    4545"Unknown",                      \
    4646"Program",                      \
    47 "Alignment",                    \
    48 "Machine check",                \
    4947"Data storage",                 \
    5048"Instruction storage",          \
     49"Alignment",                    \
     50"Other",                        \
    5151}
    5252
    5353#define CPU_TYPE_NAME powerpc
  • cpu/ppc/boot.c

     
    1919
    2020*/
    2121
     22#include <hexo/asm.h>
     23
    2224#ifdef CONFIG_SOCLIB_MEMCHECK
    2325# include <arch/mem_checker.h>
    2426#endif
    2527
    2628asm(
    27     ".section        .text,\"ax\",@progbits             \n"
     29    ".section        .text,\"ax\",@progbits     \n"
    2830
    29     ".globl cpu_boot                                    \n"
    30     "cpu_boot:                                          \n"
     31    FUNC_START(cpu_boot)
    3132
    3233    /* get CPU id and adjust stack */
    33     "lis        9, __initial_stack - 8@ha    \n"
    34     "la         1, __initial_stack - 8@l(9)  \n"
    35     "mfdcr      29,0                                    \n"
     34    "lis    9, __initial_stack - 8@ha    \n"
     35    "la     1, __initial_stack - 8@l(9)  \n"
     36    "mfdcr  29,0                         \n"
    3637
    3738#ifndef CONFIG_SMP
    3839    /* only first CPU is allowed to boot */
    39     "cmpwi      cr0, 29, 0                              \n"
    40     "1:                                                 \n"
    41     "bne        cr0, 1b                                 \n"
     40    "cmpwi  cr0, 29, 0                  \n"
     41    "1:                                 \n"
     42    "bne    cr0, 1b                     \n"
    4243#endif
    4344
    44     "rlwinm     3,29,12,0,19                            \n"
    45     "sub        1,1,3                                   \n"
     45    "rlwinm 3,29,12,0,19                \n"
     46    "sub    1,1,3                       \n"
    4647
    47         "li    3, 0                      \n"
    48         "mtmsr 3                         \n"
     48    "li    3, 0                         \n"
     49    "mtmsr 3                            \n"
    4950
    5051#ifdef CONFIG_SOCLIB_MEMCHECK
    51     "addi       2,      0,      1024            \n"
    52 /*     "lis     0, hi(" ASM_STR(SOCLIB_MC_MAGIC_VAL) ") \n" */
    53 /*     "ori     0, 0, lo(" ASM_STR(SOCLIB_MC_MAGIC_VAL) ") \n" */
    54         "lis    0, (" ASM_STR(SOCLIB_MC_MAGIC_VAL) ")@h  \n"
    55         "ori 0, 0, (" ASM_STR(SOCLIB_MC_MAGIC_VAL) ")@l  \n"
    56     "stw        0,      " ASM_STR(SOCLIB_MC_MAGIC) "(0) \n"
     52    "addi   2,  0,  1024                \n"
     53/*     "lis 0, hi(" ASM_STR(SOCLIB_MC_MAGIC_VAL) ") \n" */
     54/*     "ori 0, 0, lo(" ASM_STR(SOCLIB_MC_MAGIC_VAL) ") \n" */
     55    "lis    0, (" ASM_STR(SOCLIB_MC_MAGIC_VAL) ")@h  \n"
     56    "ori 0, 0, (" ASM_STR(SOCLIB_MC_MAGIC_VAL) ")@l  \n"
     57    "stw    0,  " ASM_STR(SOCLIB_MC_MAGIC) "(0) \n"
    5758
    58     "stw        2,      " ASM_STR(SOCLIB_MC_R2) "(0) \n"
    59     "subf       2,      2,      1                       \n"
    60     "addi       2,      2,              8                       \n"
    61     "stw        2,      " ASM_STR(SOCLIB_MC_R1) "(0) \n"
    62     "stw        29,     " ASM_STR(SOCLIB_MC_CTX_CREATE) "(0) \n"
    63     "stw        29,     " ASM_STR(SOCLIB_MC_CTX_SET) "(0) \n"
    64     "addi       0,      0,      " ASM_STR(SOCLIB_MC_CHECK_SPFP+SOCLIB_MC_CHECK_INIT) " \n"
    65     "stw        0,      " ASM_STR(SOCLIB_MC_ENABLE) "(0) \n"
     59    "stw    2,  " ASM_STR(SOCLIB_MC_R2) "(0) \n"
     60    "subf   2,  2,  1                   \n"
     61    "addi   2,  2,      8               \n"
     62    "stw    2,  " ASM_STR(SOCLIB_MC_R1) "(0) \n"
     63    "stw    29, " ASM_STR(SOCLIB_MC_CTX_CREATE) "(0) \n"
     64    "stw    29, " ASM_STR(SOCLIB_MC_CTX_SET) "(0) \n"
     65    "addi   0,  0,  " ASM_STR(SOCLIB_MC_CHECK_SPFP+SOCLIB_MC_CHECK_INIT) " \n"
     66    "stw    0,  " ASM_STR(SOCLIB_MC_ENABLE) "(0) \n"
    6667
    67     "stw        3,      " ASM_STR(SOCLIB_MC_MAGIC) "(0) \n"
     68    "stw    3,  " ASM_STR(SOCLIB_MC_MAGIC) "(0) \n"
    6869#endif
    6970
    7071    /* get device-tree and put it in arg[0] */
    7172#ifdef CONFIG_ARCH_DEVICE_TREE
    72     "lis        3, dt_blob_start@ha    \n"
    73     "la         3, dt_blob_start@l(3)  \n"
     73    "lis    3, dt_blob_start@ha          \n"
     74    "la     3, dt_blob_start@l(3)        \n"
    7475#else
    75     "li         3, 0                       \n"
     76    "li     3, 0                         \n"
    7677#endif
    7778    /* put a null in arg[1] */
    78     "li         4, 0                       \n"
     79    "li     4, 0                         \n"
    7980
    80     "lis        2, __exception_base_ptr@ha      \n"
     81    "lis    2, __exception_base_ptr@ha  \n"
    8182    "la     2, __exception_base_ptr@l(2) \n"
    82     "mtevpr 2                                   \n"
     83    "mtevpr 2                            \n"
    8384
    8485    /* jumpto arch_init function */
    85     "lis        2, arch_init@ha                         \n"
    86     "la         2, arch_init@l(2)                       \n"
    87     "mtctr      2                                       \n"
    88     "bctr                                               \n"
     86    "lis    2, arch_init@ha              \n"
     87    "la         2, arch_init@l(2)        \n"
     88    "mtctr      2                        \n"
     89    "bctr                                \n"
     90    FUNC_END(cpu_boot)
    8991    );
    9092
    9193asm(
    92     ".section        .boot,\"ax\",@progbits     \n"
     94    ".section        .boot,\"ax\",@progbits  \n\t"
    9395
    94     ".globl cpu_boot_pointer    \n\t"
    95     "cpu_boot_pointer:          \n\t"
    96         "1:                         \n\t"
    97     "lis    3, cpu_boot@ha      \n\t"
    98     "la     3, cpu_boot@l(3)    \n\t"
    99     "mtctr  3                   \n\t"
    100     "bctr                       \n\t"
    101     ".org 0x80-4                \n\t"
    102     "b      1b                  \n\t"
     96    FUNC_START(cpu_boot_pointer)
     97    "1:                                      \n\t"
     98    "lis    3, cpu_boot@ha                   \n\t"
     99    "la     3, cpu_boot@l(3)                 \n\t"
     100    "mtctr  3                                \n\t"
     101    "bctr                                    \n\t"
     102    ".org 0x80-4                             \n\t"
     103    "b      1b                               \n\t"
     104    FUNC_END(cpu_boot_pointer)
    103105    );
    104106
     107
     108// Local Variables:
     109// tab-width: 4;
     110// c-basic-offset: 4;
     111// indent-tabs-mode: nil;
     112// End:
     113//
     114// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=4:softtabstop=4
  • cpu/mips/interrupts.c

     
    1616    Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
    1717
    1818    Copyright Alexandre Becoulet <alexandre.becoulet@lip6.fr> (c) 2006
     19    Copyright (c) 2010, Nicolas Pouillon <nipo@ssji.net>
     20*/
    1921
     22#include <hexo/asm.h>
     23
     24#ifdef CONFIG_SMP
     25# define CPU_LOCAL_GET(reg, name) "    lw " #reg ", " #name "($27) \n"
     26#else
     27# define CPU_LOCAL_GET(reg, name) "    lw " #reg ", " #name "\n"
     28#endif
     29
     30#if __mips >= 32
     31# define CPU_ID(reg)                                                   \
     32    "   mfc0    " #reg ",    $15,    1           \n"                   \
     33    "   andi    " #reg ",    " #reg ",    0x3ff  \n"
     34# define STATUS_UM_BIT "0x10"
     35#else
     36# define CPU_ID(reg)                                                   \
     37    "   mfc0    " #reg ",    $15                 \n"                   \
     38    "   andi    " #reg ",    " #reg ",    0x3ff  \n"
     39# define STATUS_UM_BIT "0x8"
     40#endif
     41
     42// Not in macros: $0, $26 (k0), $27 (k1), $29 (sp)
     43
     44// 11 registers (but as we call ABI-compliant func, t* may not be saved)
     45// so only gp and ra must be saved.
     46// Even if we end-up switching threads, switch() will finally save them
     47#define DO_CALLEE_SAVED(op, reg)                 \
     48    "   " #op "  $28,   28 * 4(" #reg ") \n"     \
     49    "   " #op "  $31,   31 * 4(" #reg ") \n"
     50/*
     51    "   " #op "  $16,   16 * 4(" #reg ") \n"     \
     52    "   " #op "  $17,   17 * 4(" #reg ") \n"     \
     53    "   " #op "  $18,   18 * 4(" #reg ") \n"     \
     54    "   " #op "  $19,   19 * 4(" #reg ") \n"     \
     55    "   " #op "  $20,   20 * 4(" #reg ") \n"     \
     56    "   " #op "  $21,   21 * 4(" #reg ") \n"     \
     57    "   " #op "  $22,   22 * 4(" #reg ") \n"     \
     58    "   " #op "  $23,   23 * 4(" #reg ") \n"     \
     59    "   " #op "  $30,   30 * 4(" #reg ") \n"     \
    2060*/
    2161
     62
     63// 10 registers
     64#define DO_TEMP_REGS(op, reg)                    \
     65    "   " #op "   $8,    8 * 4(" #reg ") \n"     \
     66    "   " #op "   $9,    9 * 4(" #reg ") \n"     \
     67    "   " #op "  $10,   10 * 4(" #reg ") \n"     \
     68    "   " #op "  $11,   11 * 4(" #reg ") \n"     \
     69    "   " #op "  $12,   12 * 4(" #reg ") \n"     \
     70    "   " #op "  $13,   13 * 4(" #reg ") \n"     \
     71    "   " #op "  $14,   14 * 4(" #reg ") \n"     \
     72    "   " #op "  $15,   15 * 4(" #reg ") \n"     \
     73    "   " #op "  $24,   24 * 4(" #reg ") \n"     \
     74    "   " #op "  $25,   25 * 4(" #reg ") \n"
     75
     76#define DO_AT_REG(op, reg)                       \
     77    "   " #op "   $1,    1 * 4(" #reg ") \n"
     78
     79#define DO_RVAL_REGS(op, reg)                    \
     80    "   " #op "   $2,    2 * 4(" #reg ") \n"     \
     81    "   " #op "   $3,    3 * 4(" #reg ") \n"
     82
     83#define DO_ARG_REGS(op, reg)                     \
     84    "   " #op "   $4,    4 * 4(" #reg ") \n"     \
     85    "   " #op "   $5,    5 * 4(" #reg ") \n"     \
     86    "   " #op "   $6,    6 * 4(" #reg ") \n"     \
     87    "   " #op "   $7,    7 * 4(" #reg ") \n"
     88
    2289asm(
    2390        ".section        .excep,\"ax\",@progbits         \n"
    2491
    2592        ".set push                                       \n"
    2693        ".set noreorder                                  \n"
    2794        "   b       1f                                   \n"
    28 # if __mips >= 32
     95#if __mips >= 32
    2996        ".space 0x17c                                    \n"
    3097#else
    3198        ".space 0x7c                                     \n"
    3299#endif
    33100        ".set pop                                        \n"
    34101
    35         ".globl mips_interrupt_entry                     \n"
    36         ".func mips_interrupt_entry                      \n"
    37         ".type mips_interrupt_entry, %function           \n"
    38         "mips_interrupt_entry:                           \n"
     102        FUNC_START(mips_interrupt_entry)
    39103        ".set push                                       \n"
    40104        ".set noat                                       \n"
    41105
     
    43107
    44108        /* restore cpu local storage */
    45109#if defined(CONFIG_CPU_USER)
    46 # if defined(CONFIG_SMP)
    47110
    48 #  if __mips >= 32
    49         "   mfc0    $26,    $15,    1                    \n"
    50 #  else
    51         "   mfc0    $26,    $15                          \n"
    52 #  endif
    53 
    54         "   andi    $26,    $26,    0x3ff                \n"
    55         "   sll     $26,    $26,    2                    \n"
    56         "   lw      $27,    cpu_local_storage($26)       \n"
    57 # endif
    58 
    59111        /* event from user mode ? */
    60112        "   mfc0    $26,    $12                          \n"
    61         "   andi    $26,    $26,    0x8                  \n"
     113        "   andi    $26,    $26,  " STATUS_UM_BIT "      \n"
    62114
    63115        ".set noreorder                                  \n"
    64         "   blez    $26,    1f                           \n"
     116        /* zero if from Kernel mode */
     117        "   beqz    $26,    1f                           \n"
     118        /* abuse the delay slot to get the current SP (sp_user_kernel) */
    65119        "   move    $26,    $sp                          \n"
    66120        ".set reorder                                    \n"
    67121
     122# if defined(CONFIG_SMP)
     123        /* Restore CLS if we are from user mode */
     124        CPU_ID($26)
     125        "   sll     $26,    $26,    2                    \n"
     126        "   lw      $27,    cpu_local_storage($26)       \n"
     127# endif
     128
     129        /* Get user's SP (sp_user_user) */
     130        "   move    $26,    $sp                          \n"
     131
    68132        /* restore kernel stack ! */
    69 # ifdef CONFIG_SMP
    70         "   lw      $sp,    __context_data_base($27) \n"
    71 # else
    72         "   lw      $sp,    __context_data_base      \n"
    73 # endif
    74         "   addiu   $sp,    %lo(context_kstack)          \n"
    75         "   lw      $sp,    ($sp)                        \n"
     133        CPU_LOCAL_GET($sp, __context_data_base)
     134        "   lw      $sp,    %lo(context_kstack)($sp)     \n"
     135        "1:                                              \n"
    76136#else  /* !defined(CONFIG_CPU_USER) */
     137        /* Get current SP (sp_user_none) */
    77138        "   move    $26,    $sp                          \n"
    78139#endif
    79140
    80         /* save registers usefull to syscall */
    81         "1:                                              \n"
    82         "   addu    $sp,    -4*32                        \n"
     141        /*
     142          Either:
     143          * We are not handling user mode and $26 is last known sp (sp_user_none)
     144          * We are handling user mode
     145           * From user mode, $26 is user's sp (sp_user_user)
     146           * From kernel mode, $26 is last known sp (sp_user_kernel)
     147         */
     148
     149        /* save registers useful to syscall */
    83150#if defined(CONFIG_LIBELF_RTLD_TLS)
    84151        /* add room for hwrena and tls registers */
    85         "   addu    $sp,    -4*2                         \n"
     152        "   addu    $sp,    -4*35                        \n"
     153#else
     154        "   addu    $sp,    -4*33                        \n"
    86155#endif
    87156        "   sw      $26,    29*4($sp)                    \n"
    88157
    89         "   sw      $4,     4*4($sp)                     \n" /* Args regs */
    90         "   sw      $5,     5*4($sp)                     \n" /* Args regs */
    91         "   sw      $6,     6*4($sp)                     \n" /* Args regs */
    92         "   sw      $7,     7*4($sp)                     \n" /* Args regs */
     158        DO_ARG_REGS(sw, $sp)
    93159
    94         "   sw      $31,    31*4($sp)                    \n" /* Return address regs */
    95 
    96160        /* read and extract cause */
    97161        "   mfc0    $4,     $13                          \n"
    98162        "   andi    $6,     $4,     0x3c                 \n"
    99163
    100         /* read & save EPC */
    101         "   mfc0    $5,     $14                          \n"
    102         "   sw      $5,     0*4($sp)                     \n"
     164        "   mfc0    $5,     $12                          \n"
     165        "   sb      $5,     32*4($sp)                    \n"
     166        /* Let's say we are in kernel mode, no exception, no irq */
     167# if __mips >= 32
     168        "   ori     $5,     $5,     0x1f                 \n"
     169        "   xori    $5,     $5,     0x1f                 \n"
     170# else
     171#  error Implement me
     172# endif
     173        "   mtc0    $5,     $12                          \n"
    103174
    104175#if defined(CONFIG_LIBELF_RTLD_TLS)
    105176        /* read & save hwrena */
    106177        "   mfc0    $7,     $7                           \n"
    107         "   sw      $7,     32*4($sp)                    \n"
     178        "   sw      $7,     33*4($sp)                    \n"
    108179        /* read & save tls */
    109180        "   mfc0    $7,     $4, 2                        \n"
    110         "   sw      $7,     33*4($sp)                    \n"
     181        "   sw      $7,     34*4($sp)                    \n"
    111182#endif
    112183
     184#if defined(CONFIG_CPU_USER)
     185        /* increment the user-mode counter */
     186        CPU_LOCAL_GET($5, __context_data_base)
     187        "   lw      $7,     %lo(usermode_counter)($5)    \n"
     188        "   addui   $7,     $7, 1                        \n"
     189        "   sw      $7,     %lo(usermode_counter)($5)    \n"
     190#endif
     191
    113192        "   li      $7,     32                           \n"
    114193        "   beq     $6,     $7,     interrupt_sys        \n"
    115194
    116195        /* save extra registers for hw interrupts and exceptions only */
    117196
    118         "   sw      $1,     1*4($sp)                     \n" /* AT reg */
     197        DO_AT_REG(sw, $sp)
     198        DO_RVAL_REGS(sw, $sp)
     199        DO_TEMP_REGS(sw, $sp)
     200        DO_CALLEE_SAVED(sw, $sp)
    119201
    120         "   sw      $2,     2*4($sp)                     \n" /* Return value regs */
    121         "   sw      $3,     3*4($sp)                     \n" /* Return value regs */
     202        /* read & save EPC */
     203        "   mfc0    $5,     $14                          \n"
     204        "   sw      $5,     0*4($sp)                     \n"
    122205
    123         "   sw      $8,     8*4($sp)                     \n" /* Temp regs */
    124         "   sw      $9,     9*4($sp)                     \n" /* Temp regs */
    125         "   sw      $10,    10*4($sp)                    \n" /* Temp regs */
    126         "   sw      $11,    11*4($sp)                    \n" /* Temp regs */
    127         "   sw      $12,    12*4($sp)                    \n" /* Temp regs */
    128         "   sw      $13,    13*4($sp)                    \n" /* Temp regs */
    129         "   sw      $14,    14*4($sp)                    \n" /* Temp regs */
    130         "   sw      $15,    15*4($sp)                    \n" /* Temp regs */
    131 
    132         "   sw      $16,    16*4($sp)                    \n" /* Callee saved */
    133         "   sw      $17,    17*4($sp)                    \n" /* Callee saved */
    134         "   sw      $18,    18*4($sp)                    \n" /* Callee saved */
    135         "   sw      $19,    19*4($sp)                    \n" /* Callee saved */
    136         "   sw      $20,    20*4($sp)                    \n" /* Callee saved */
    137         "   sw      $21,    21*4($sp)                    \n" /* Callee saved */
    138         "   sw      $22,    22*4($sp)                    \n" /* Callee saved */
    139         "   sw      $23,    23*4($sp)                    \n" /* Callee saved */
    140 
    141         "   sw      $30,    30*4($sp)                    \n" /* Callee saved */
    142 
    143         "   sw      $24,    24*4($sp)                    \n" /* Temp regs */
    144         "   sw      $25,    25*4($sp)                    \n" /* Temp regs */
    145 
    146         "   sw      $28,    28*4($sp)                    \n" /* Save user GP */
    147 
    148206        "   beq     $6,     $0,     interrupt_hw         \n"
    149207
    150208        /*************************************************************
    151209          exception handling
    152210         **************************************************************/
    153 
    154211        "interrupt_ex:                                   \n"
    155212
    156213        /* exception function arguments */
    157         "   srl     $4,     $6,     2                    \n" /* adjust cause arg */
    158         //"   move    $5,     $5                           \n" /* execution pointer */
    159         "   mfc0    $6,     $8                           \n" /* bad address if any */
    160         "   addiu   $7,     $sp,    0                    \n" /* register table on stack */
     214        /* adjust cause arg */
     215        "   srl     $4,     $6,     2                    \n"
     216        /* execution pointer */
     217        //"   move    $5,     $5                           \n"
     218        /* bad address if any */
     219        "   mfc0    $6,     $8                           \n"
     220        /* register table on stack */
     221        "   addiu   $7,     $sp,    0                    \n"
    161222
    162223        "   addiu   $sp,    $sp,    -5*4                 \n"
    163224        "   sw      $26,    4*4($sp)                     \n"
    164 #ifdef CONFIG_SMP
    165         "   lw      $1,     cpu_exception_handler($27)   \n"
    166 #else
    167         "   lw      $1,     cpu_exception_handler        \n"
    168 #endif
     225        CPU_LOCAL_GET($1, cpu_exception_handler)
    169226        "   jalr    $1                                   \n"
    170227        "   addiu   $sp,    $sp,    5*4                  \n"
    171228
    172         "   lw      $26,    0*4($sp)                     \n" /* get EPC value */
     229        /* get EPC value */
     230        "   lw      $26,    0*4($sp)                     \n"
    173231
    174232        "   j       return                               \n"
    175233
     
    178236         **************************************************************/
    179237        "interrupt_sys:                                  \n"
    180238
    181         "   move    $4,     $0                           \n" /* single trap on mips: id = 0 */
    182         "   addiu   $5,     $sp,    0                    \n" /* register table on stack */
     239        /* single trap on mips: id = 0 */
     240        "   move    $4,     $0                           \n"
     241        /* register table on stack */
     242        "   addiu   $5,     $sp,    0                    \n"
    183243        "   addiu   $sp,    $sp,    -4*4                 \n"
    184 #ifdef CONFIG_SMP
    185         "   lw      $11,    __context_data_base($27) \n"
    186 #else
    187         "   lw      $11,    __context_data_base      \n"
    188 #endif
     244        CPU_LOCAL_GET($31, __context_data_base)
    189245        "   lw      $1,     cpu_syscall_handler($11)     \n"
    190246        "   jalr    $1                                   \n"
    191247        "   addiu   $sp,    $sp,    4*4                  \n"
    192248
    193         "   lw      $26,    0*4($sp)                     \n" /* get EPC value */
    194         "   addiu   $26,    4                            \n" /* increment epc for not doing the syscall again */
     249        /* get EPC value */
     250        "   lw      $26,    0*4($sp)                     \n"
     251        /* increment epc for not doing the syscall again */
     252        "   addiu   $26,    4                            \n"
    195253
    196254#ifdef CONFIG_SYSCALL_CLEAN_REGS
    197255        /* FIXME cleanup all caller saved registers here */
     
    204262         **************************************************************/
    205263        "interrupt_hw:                                   \n"
    206264
    207         "   srl     $5,     $4,     10                   \n" /* hw interrupt line id */
     265        /* hw interrupt line id */
     266        "   srl     $5,     $4,     10                   \n"
    208267        "   andi    $5,     $5,     0xff                 \n"
    209268
    210269        "   addiu   $sp,    $sp,    -4*4                 \n"
    211 #ifdef CONFIG_SMP
    212         "   lw      $1,     cpu_interrupt_handler($27)   \n"
    213         "   lw      $4,     cpu_interrupt_handler_arg($27)\n"
    214 #else
    215         "   lw      $1,     cpu_interrupt_handler        \n"
    216         "   lw      $4,     cpu_interrupt_handler_arg    \n"
    217 #endif
     270        CPU_LOCAL_GET($1, cpu_interrupt_handler)
     271        CPU_LOCAL_GET($4, cpu_interrupt_handler_arg)
    218272        "   jalr    $1                                   \n"
    219273        "   addiu   $sp,    $sp,    4*4                  \n"
    220274
    221         "   lw      $26,    0*4($sp)                     \n" /* get EPC value */
     275        /* get EPC value */
     276        "   lw      $26,    0*4($sp)                     \n"
    222277
    223278        /************************************************************/
    224 
    225279        /* restore registers */
    226280        "return:                                         \n"
    227281
    228         "   lw      $1,     1*4($sp)                     \n"
     282        DO_AT_REG(lw, $sp)
     283        DO_ARG_REGS(lw, $sp)
     284        DO_TEMP_REGS(lw, $sp)
    229285
    230         "   lw      $4,     4*4($sp)                     \n"
    231         "   lw      $5,     5*4($sp)                     \n"
    232         "   lw      $6,     6*4($sp)                     \n"
    233         "   lw      $7,     7*4($sp)                     \n"
     286        "return_val:                                     \n"
    234287
    235         "   lw      $8,     8*4($sp)                     \n"
    236         "   lw      $9,     9*4($sp)                     \n"
    237         "   lw      $10,    10*4($sp)                    \n"
    238         "   lw      $11,    11*4($sp)                    \n"
    239         "   lw      $12,    12*4($sp)                    \n"
    240         "   lw      $13,    13*4($sp)                    \n"
    241         "   lw      $14,    14*4($sp)                    \n"
    242         "   lw      $15,    15*4($sp)                    \n"
     288        DO_RVAL_REGS(lw, $sp)
    243289
    244         "   lw      $16,    16*4($sp)                    \n"
    245         "   lw      $17,    17*4($sp)                    \n"
    246         "   lw      $18,    18*4($sp)                    \n"
    247         "   lw      $19,    19*4($sp)                    \n"
    248         "   lw      $20,    20*4($sp)                    \n"
    249         "   lw      $21,    21*4($sp)                    \n"
    250         "   lw      $22,    22*4($sp)                    \n"
    251         "   lw      $23,    23*4($sp)                    \n"
     290        /* reload lower byte of status */
     291        "   lbu     $28,    32*4($sp)                    \n"
     292        "   mfc0    $31,    $12                          \n"
     293        "   ori     $31,    $31,    0xff                 \n"
     294        "   xori    $31,    $31,    0xff                 \n"
     295        "   or      $31,    $31,    $28                  \n"
     296        "   mtc0    $31,    $12                          \n"
    252297
    253         "   lw      $30,    30*4($sp)                    \n"
    254 
    255         "   lw      $24,    24*4($sp)                    \n"
    256         "   lw      $25,    25*4($sp)                    \n"
    257 
    258         "return_val:                                     \n"
    259 
    260         "   lw      $2,     2*4($sp)                     \n" /* Syscall return value */
    261         "   lw      $3,     3*4($sp)                     \n" /* Syscall return value */
    262 
    263298#if defined(CONFIG_LIBELF_RTLD_TLS)
    264299        /* reload hwrena */
    265         "   lw      $31,    32*4($sp)                    \n"
     300        "   lw      $31,    33*4($sp)                    \n"
    266301        "   mtc0    $31,    $7                           \n"
    267302        /* reload tls */
    268         "   lw      $31,    33*4($sp)                    \n"
     303        "   lw      $31,    34*4($sp)                    \n"
    269304        "   mtc0    $31,    $4, 2                        \n"
    270305#endif
    271306
    272         "   lw      $28,    28*4($sp)                    \n" /* restore user GP */
    273         "   lw      $31,    31*4($sp)                    \n" /* restore return address */
     307        DO_CALLEE_SAVED(lw, $sp)
    274308
    275         "   lw      $sp,    29*4($sp)                    \n" /* restore user stack */
     309        /* restore user stack */
     310        "   lw      $sp,    29*4($sp)                    \n"
    276311
    277312# if __mips >= 32
    278313        /* restore epc for eret */
     
    285320# endif
    286321
    287322        ".set pop                                        \n"
    288                 ".endfunc                                        \n"
    289         ".size mips_interrupt_entry, .-mips_interrupt_entry \n"
     323        FUNC_END(mips_interrupt_entry)
    290324        );
    291325
    292         // Local Variables:
    293         // tab-width: 4;
    294         // c-basic-offset: 4;
    295         // c-file-offsets:((innamespace . 0)(inline-open . 0));
    296         // indent-tabs-mode: nil;
    297         // End:
    298         //
    299         // vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=4:softtabstop=4
     326// Local Variables:
     327// tab-width: 4;
     328// c-basic-offset: 4;
     329// indent-tabs-mode: nil;
     330// End:
     331//
     332// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=4:softtabstop=4
    300333
  • cpu/mips/include/cpu/hexo/interrupt.h

     
    198198#endif
    199199}
    200200
     201#define CPU_EXCEPTION_DATA_ALIGN   0x4 // ADEL
     202#define CPU_EXCEPTION_INS_ERROR    0x6 // IBE
     203#define CPU_EXCEPTION_DATA_ERROR   0x7 // DBE
     204#define CPU_EXCEPTION_BREAKPOINT   0x9 // Bp
     205#define CPU_EXCEPTION_ILLEGAL_INS  0xa // RI
     206#define CPU_EXCEPTION_COPROC       0xb // CpU
     207#define CPU_EXCEPTION_TRAP         0xd // Tr
     208#define CPU_EXCEPTION_FPE          0xf // FPE
     209
    201210#endif
    202211
  • cpu/mips/include/cpu/hexo/context.h

     
    7070                "       sw      $15,    0*4($sp)        \n"
    7171                /* switch stack pointer */
    7272                "       sw      $sp,    (%0)            \n"
     73#ifdef CONFIG_SOCLIB_MEMCHECK
    7374                "       lw      $15,    (%1)            \n"
    74 #ifdef CONFIG_SOCLIB_MEMCHECK
    7575                        /* let memchecker know about context switch */
    7676                "       li      $1,     " ASM_STR(SOCLIB_MC_MAGIC_VAL) " \n"
    7777                "       sw      $1,     " ASM_STR(SOCLIB_MC_MAGIC) "($0) \n"
    7878                "       sw      %1,     " ASM_STR(SOCLIB_MC_CTX_SET) "($0) \n"
    7979                "       ori     $1,     $0,     " ASM_STR(SOCLIB_MC_CHECK_SPFP) " \n"
    8080                "       sw      $1,     " ASM_STR(SOCLIB_MC_ENABLE) "($0) \n"
    81 #endif
    8281                "       move    $sp,    $15             \n"
    83 #ifdef CONFIG_SOCLIB_MEMCHECK
    8482                "       sw      $0,     " ASM_STR(SOCLIB_MC_MAGIC) "($0) \n"
     83#else
     84                "       lw      $sp,    (%1)            \n"
    8585#endif
    8686                /* restore status & tls */
    8787                "       lw      $1,     1*4($sp)        \n"
  • cpu/mips/boot.c

     
    1919
    2020*/
    2121
     22#include <hexo/asm.h>
     23
    2224#ifdef CONFIG_SOCLIB_MEMCHECK
    2325# include <arch/mem_checker.h>
    2426#endif
     
    2628asm(
    2729        ".section        .boot,\"ax\",@progbits                                            \n"
    2830
    29         ".globl cpu_boot                                                                   \n"
    30         ".func cpu_boot                             \n\t"
    31         ".type   cpu_boot, %function    \n\t"
    32         "cpu_boot:                                                                         \n"
     31        FUNC_START(cpu_boot)
    3332
    3433        ".set push                                                                         \n"
    3534        ".set noreorder                                                                    \n"
     
    122121#endif
    123122
    124123        ".set pop                                                                          \n"
    125         ".size   cpu_boot, .-cpu_boot   \n\t"
    126         ".endfunc \n\t"
     124        FUNC_END(cpu_boot)
    127125);
    128126
    129127// Local Variables:
  • cpu/mips/cpu_context.c

     
    77# include <arch/mem_checker.h>
    88#endif
    99
    10 #if defined(CONFIG_CPU_USER)
    11 CONTEXT_LOCAL uintptr_t context_kstack;
    12 #endif
    13 
    1410error_t
    1511cpu_context_bootstrap(struct context_s *context)
    1612{
  • hexo/include/hexo/asm.h

     
     1/*
     2 * This file is part of MutekH.
     3 *
     4 * MutekH is free software; you can redistribute it and/or modify it
     5 * under the terms of the GNU Lesser General Public License as published
     6 * by the Free Software Foundation; version 2.1 of the License.
     7 *
     8 * MutekH is distributed in the hope that it will be useful, but
     9 * WITHOUT ANY WARRANTY; without even the implied warranty of
     10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
     11 * Lesser General Public License for more details.
     12 *
     13 * You should have received a copy of the GNU Lesser General Public
     14 * License along with MutekH; if not, write to the Free Software
     15 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
     16 * 02110-1301 USA
     17 *
     18 * Copyright (c) UPMC, Lip6, SoC
     19 *         Nicolas Pouillon <nipo@ssji.net>, 2010
     20 */
     21
     22#ifndef HEXO_ASM_H_
     23#define HEXO_ASM_H_
     24
     25#define ASM_STR_(x) #x
     26#define ASM_STR(x) ASM_STR_(x)
     27
     28#define FUNC_START(x)                             \
     29        "\t.globl " #x "            \n"           \
     30        "\t.func " #x "             \n"           \
     31        "\t.type " #x ", %function  \n"           \
     32        #x ":                     \n"
     33
     34#define FUNC_END(x)                           \
     35    "\t.endfunc               \n"             \
     36    "\t.size " #x ", .-" #x " \n"
     37
     38#endif
  • hexo/user_mode.c

    Property changes on: hexo/include/hexo/asm.h
    ___________________________________________________________________
    Added: svn:mime-type
       + text/plain
    Added: svn:keywords
       + "Author Date Id Rev URL Revision"
    Added: svn:eol-style
       + native
    
     
     1/*
     2 * This file is part of MutekH.
     3 *
     4 * MutekH is free software; you can redistribute it and/or modify it
     5 * under the terms of the GNU Lesser General Public License as published
     6 * by the Free Software Foundation; version 2.1 of the License.
     7 *
     8 * MutekH is distributed in the hope that it will be useful, but
     9 * WITHOUT ANY WARRANTY; without even the implied warranty of
     10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
     11 * Lesser General Public License for more details.
     12 *
     13 * You should have received a copy of the GNU Lesser General Public
     14 * License along with MutekH; if not, write to the Free Software
     15 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
     16 * 02110-1301 USA
     17 *
     18 * Copyright (c) UPMC, Lip6, SoC
     19 *         Nicolas Pouillon <nipo@ssji.net>, 2010
     20 */
     21
     22#include <hexo/types.h>
     23#include <hexo/local.h>
     24
     25/**
     26   Pointer to base of kernel stack associated to a user-mode thread
     27 */
     28CONTEXT_LOCAL uintptr_t context_kstack;
  • hexo/Makefile

    Property changes on: hexo/user_mode.c
    ___________________________________________________________________
    Added: svn:mime-type
       + text/plain
    Added: svn:keywords
       + "Author Date Id Rev URL Revision"
    Added: svn:eol-style
       + native
    
     
    88objs += ipi.o
    99endif
    1010
     11ifeq ($(CONFIG_CPU_USER), defined)
     12objs += user_mode.o
     13endif
     14
    1115ifeq ($(CONFIG_HEXO_IRQ), defined)
    1216objs += interrupt.o
    1317endif
  • drivers/device/icu/sam7/icu-sam7.c

     
    9292
    9393DEV_IRQ(icu_sam7_handler)
    9494{
     95#if !defined(CONFIG_CPU_ARM_CUSTOM_IRQ_HANDLER)
    9596        AT91PS_AIC registers = (void*)dev->addr[0];
    9697//      struct icu_sam7_private_s       *pv = dev->drv_pv;
    9798//      struct icu_sam7_handler_s       *h = pv->table[irq];
     
    110111
    111112//      registers->AIC_EOICR = 0;
    112113
     114#endif
    113115        return 0;
    114116}
    115117
     
    156158REGISTER_DRIVER(icu_sam7_drv);
    157159#endif
    158160
    159 #if 0
    160 static
    161 __attribute__ ((interrupt ("IRQ")))
    162 void sam7_spurious_irq_handler()
    163 {
    164         uint32_t irq;
    165         asm("ldr %0, [sp, #6*4]": "=r" (irq));
    166         kputs("SAM7 lost spurious interrupt\n");
    167         cpu_mem_write_32(0xfffff130, 1);
    168 }
    169 #endif
    170 
     161#if defined(CONFIG_CPU_ARM_CUSTOM_IRQ_HANDLER)
    171162struct device_s *sam7_c_irq_dev;
    172163
    173164__attribute__ ((interrupt ("IRQ")))
     
    193184                h->hndl(h->data);
    194185        registers->AIC_EOICR = 1;
    195186}
     187#endif
    196188
    197189DEV_INIT(icu_sam7_init)
    198190{
  • drivers/device/icu/sam7/icu-sam7.config

     
    44default undefined
    55depend CONFIG_ARCH_SIMPLE_SAM7
    66provide CONFIG_DRIVER_ICU
     7provide CONFIG_CPU_ARM_CUSTOM_IRQ_HANDLER
    78%config end
    89