source: rtems/cpukit/score/cpu/arm/cpu_asm.S @ f172fc8

4.104.114.84.95
Last change on this file since f172fc8 was aed1db6c, checked in by Jay Monkman <jtm@…>, on Jun 2, 2006 at 9:49:36 PM

2006-06-02 Jay Monkman <jtm@…>

  • cpu.c, cpu_asm.S: Fixed ARM Data Abort handling.
  • Property mode set to 100644
File size: 4.6 KB
Line 
1/*
2 *  $Id$
3 *
4 *  This file contains all assembly code for the ARM implementation
5 *  of RTEMS.
6 *
7 *  Copyright (c) 2002 by Advent Networks, Inc.
8 *          Jay Monkman <jmonkman@adventnetworks.com>
9 *
10 *  COPYRIGHT (c) 2000 Canon Research Centre France SA.
11 *  Emmanuel Raguet, mailto:raguet@crf.canon.fr
12 *
13 *  The license and distribution terms for this file may be
14 *  found in the file LICENSE in this distribution or at
15 *  http://www.rtems.com/license/LICENSE.
16 *
17 */
18
19#include <rtems/asm.h>
20#include <rtems/score/cpu_asm.h>
21
22
23/*
24 *  void _CPU_Context_switch( run_context, heir_context )
25 *  void _CPU_Context_restore( run_context, heir_context )
26 *
27 *  This routine performs a normal non-FP context.
28 *
29 *  R0 = run_context    R1 = heir_context
30 *
31 *  This function copies the current registers to where r0 points, then
32 *  restores the ones from where r1 points.
33 *
34 *  Using the ldm/stm opcodes save 2-3 us on 100 MHz ARM9TDMI with
35 *  a 16 bit data bus.
36 *       
37 */
38        .globl _CPU_Context_switch
39_CPU_Context_switch:
40/* Start saving context */
41        mrs     r2, cpsr
42        stmia   r0,  {r2, r4, r5, r6, r7, r8, r9, r10, r11, r13, r14}
43
44
45/* Start restoring context */
46_restore:       
47        ldmia   r1,  {r2, r4, r5, r6, r7, r8, r9, r10, r11, r13, r14}
48        msr     cpsr, r2
49        mov     pc, lr
50
51/*
52 *  void _CPU_Context_restore( new_context )
53 *
54 *  This function copies the restores the registers from where r0 points.
55 *  It must match _CPU_Context_switch()
56 *
57 */
58        .globl _CPU_Context_restore
59_CPU_Context_restore:
60        mov     r1, r0
61        b       _restore
62
63
64
65/* FIXME:       _Exception_Handler_Undef_Swi is untested */
66        .globl _Exception_Handler_Undef_Swi
67_Exception_Handler_Undef_Swi:
68/* FIXME: This should use load and store multiple instructions */
69        sub     r13,r13,#SIZE_REGS
70        str     r4,  [r13, #REG_R4]
71        str     r5,  [r13, #REG_R5]
72        str     r6,  [r13, #REG_R6]
73        str     r7,  [r13, #REG_R7]
74        str     r8,  [r13, #REG_R8]
75        str     r9,  [r13, #REG_R9]
76        str     r10, [r13, #REG_R10]
77        str     r11, [r13, #REG_R11]
78        str     sp,  [r13, #REG_SP]
79        str     lr,  [r13, #REG_LR]
80        mrs     r0,  cpsr               /* read the status */
81        and     r0,  r0,#0x1f           /* we keep the mode as exception number */
82        str     r0,  [r13, #REG_PC]     /* we store it in a free place */
83        mov     r0,  r13                /* put frame address in r0 (C arg 1) */
84
85        ldr     r1, =SWI_Handler
86        ldr     lr, =_go_back_1
87        ldr     pc,[r1]                         /* call handler  */
88_go_back_1:
89        ldr     r4,  [r13, #REG_R4]
90        ldr     r5,  [r13, #REG_R5]
91        ldr     r6,  [r13, #REG_R6]
92        ldr     r7,  [r13, #REG_R7]
93        ldr     r8,  [r13, #REG_R8]
94        ldr     r9,  [r13, #REG_R9]
95        ldr     r10, [r13, #REG_R10]
96        ldr     r11, [r13, #REG_R11]
97        ldr     sp,  [r13, #REG_SP]
98        ldr     lr,  [r13, #REG_LR]
99        add     r13,r13,#SIZE_REGS
100        movs    pc,r14                  /* return  */
101       
102/* FIXME:       _Exception_Handler_Abort is untested */
103        .globl _Exception_Handler_Abort
104_Exception_Handler_Abort:
105/* FIXME: This should use load and store multiple instructions */
106        sub     r13,r13,#SIZE_REGS
107        str     r4,  [r13, #REG_R4]
108        str     r5,  [r13, #REG_R5]
109        str     r6,  [r13, #REG_R6]
110        str     r7,  [r13, #REG_R7]
111        str     r8,  [r13, #REG_R8]
112        str     r9,  [r13, #REG_R9]
113        str     sp,  [r13, #REG_R11]
114        str     lr,  [r13, #REG_SP]
115        str     lr,  [r13, #REG_LR]
116        mrs     r0,  cpsr               /* read the status */
117        and     r0,  r0,#0x1f           /* we keep the mode as exception number */
118        str     r0,  [r13, #REG_PC]     /* we store it in a free place */
119        mov     r0,  r13                /* put frame address in ro (C arg 1) */
120       
121        ldr     r1, =_currentExcHandler
122        ldr     lr, =_go_back_2
123        ldr     pc,[r1]                         /* call handler  */
124_go_back_2:
125        ldr     r4,  [r13, #REG_R4]
126        ldr     r5,  [r13, #REG_R5]
127        ldr     r6,  [r13, #REG_R6]
128        ldr     r7,  [r13, #REG_R7]
129        ldr     r8,  [r13, #REG_R8]
130        ldr     r9,  [r13, #REG_R9]
131        ldr     r10, [r13, #REG_R10]
132        ldr     sp,  [r13, #REG_R11]
133        ldr     lr,  [r13, #REG_SP]
134        ldr     lr,  [r13, #REG_LR]
135        add     r13,r13,#SIZE_REGS
136        subs    pc,r14,#4                       /* return */
137
138#define ABORT_REGS_OFFS 32-REG_R4
139#define ABORT_SIZE_REGS SIZE_REGS+ABORT_REGS_OFFS
140       
141        .globl _exc_data_abort
142_exc_data_abort:
143        sub     sp, sp, #ABORT_SIZE_REGS        /* reserve register frame */
144        stmia   sp, {r0-r11}
145        add     sp, sp, #ABORT_REGS_OFFS        /* the Context_Control structure starts by CPSR, R4, ... */
146
147        str     ip, [sp, #REG_PC]               /* store R12 (ip) somewhere, oh hackery, hackery, hack */
148        str     lr, [sp, #REG_LR]
149
150        mov     r1, lr
151        ldr     r0, [r1, #-8]                   /* r0 = bad instruction */
152        mrs     r1, spsr                        /* r1 = spsr */
153        mov     r2, r13                         /* r2 = exception frame of Context_Control type */
154        bl      do_data_abort
155       
156        ldr     lr, [sp, #REG_LR]
157        ldr     ip, [sp, #REG_PC]               /* restore R12 (ip) */
158
159        sub     sp, sp, #ABORT_REGS_OFFS
160        ldmia   sp, {r0-r11}
161        add     sp, sp, #ABORT_SIZE_REGS
162
163        subs    pc, r14, #4                     /* return to the instruction */
164                                                /* _AFTER_ the aborted one */
Note: See TracBrowser for help on using the repository browser.