2b3b7f485e8fdf4bcc499751a0cdada424203212
[openocd.git] / testing / examples / STR710Test / src / crt.s
1 /****************************************************************************\r
2 *  Copyright (c) 2006 by Michael Fischer. All rights reserved.\r
3 *\r
4 *  Redistribution and use in source and binary forms, with or without \r
5 *  modification, are permitted provided that the following conditions \r
6 *  are met:\r
7 *  \r
8 *  1. Redistributions of source code must retain the above copyright \r
9 *     notice, this list of conditions and the following disclaimer.\r
10 *  2. Redistributions in binary form must reproduce the above copyright\r
11 *     notice, this list of conditions and the following disclaimer in the \r
12 *     documentation and/or other materials provided with the distribution.\r
13 *  3. Neither the name of the author nor the names of its contributors may \r
14 *     be used to endorse or promote products derived from this software \r
15 *     without specific prior written permission.\r
16 *\r
17 *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \r
18 *  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT \r
19 *  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS \r
20 *  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL \r
21 *  THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, \r
22 *  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, \r
23 *  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS \r
24 *  OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED \r
25 *  AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, \r
26 *  OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF \r
27 *  THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF \r
28 *  SUCH DAMAGE.\r
29 *\r
30 ****************************************************************************\r
31 *\r
32 *  History:\r
33 *\r
34 *  04.03.06  mifi   First Version\r
35 *                   This version based on an example from Ethernut and\r
36 *                   "ARM Cross Development with Eclipse" from James P. Lynch\r
37 *\r
38 *  26.01.08  mifi   Change the code of the init section. Here I have used\r
39 *                   some of the source from the Anglia startup.s\r
40 *                   Author: Spencer Oliver (www.anglia-designs.com)\r
41 ****************************************************************************/\r
42 \r
43 /*\r
44  * Some defines for the program status registers\r
45  */\r
46    ARM_MODE_USER  = 0x10      /* Normal User Mode                                                      */ \r
47    ARM_MODE_FIQ   = 0x11      /* FIQ Fast Interrupts Mode                                        */\r
48    ARM_MODE_IRQ   = 0x12      /* IRQ Standard Interrupts Mode                            */\r
49    ARM_MODE_SVC   = 0x13      /* Supervisor Interrupts Mode                              */\r
50    ARM_MODE_ABORT = 0x17      /* Abort Processing memory Faults Mode               */\r
51    ARM_MODE_UNDEF = 0x1B      /* Undefined Instructions Mode                        */\r
52    ARM_MODE_SYS   = 0x1F      /* System Running in Priviledged Operating Mode */\r
53    ARM_MODE_MASK  = 0x1F\r
54    \r
55    I_BIT          = 0x80      /* disable IRQ when I bit is set */\r
56    F_BIT          = 0x40      /* disable IRQ when I bit is set */\r
57    \r
58 /*\r
59  * Register Base Address\r
60  */\r
61    PRCCU_BASE     = 0xA0000000\r
62    RCCU_CFR       = 0x08\r
63    RCCU_PLL1CR    = 0x18\r
64    PCU_MDIVR      = 0x40\r
65    PCU_PDIVR      = 0x44\r
66    PCU_BOOTCR     = 0x50\r
67           \r
68       \r
69    .section .vectors,"ax"\r
70    .code 32\r
71         \r
72 /****************************************************************************/\r
73 /*               Vector table and reset entry                               */\r
74 /****************************************************************************/\r
75 _vectors:\r
76    ldr pc, ResetAddr    /* Reset                 */\r
77    ldr pc, UndefAddr    /* Undefined instruction */\r
78    ldr pc, SWIAddr      /* Software interrupt    */\r
79    ldr pc, PAbortAddr   /* Prefetch abort        */\r
80    ldr pc, DAbortAddr   /* Data abort            */\r
81    ldr pc, ReservedAddr /* Reserved              */\r
82    ldr pc, IRQAddr      /* IRQ interrupt         */\r
83    ldr pc, FIQAddr      /* FIQ interrupt         */\r
84 \r
85 \r
86 ResetAddr:     .word ResetHandler\r
87 UndefAddr:     .word UndefHandler\r
88 SWIAddr:       .word SWIHandler\r
89 PAbortAddr:    .word PAbortHandler\r
90 DAbortAddr:    .word DAbortHandler\r
91 ReservedAddr:  .word 0\r
92 IRQAddr:       .word IRQHandler\r
93 FIQAddr:       .word FIQHandler\r
94 \r
95    .ltorg\r
96 \r
97 \r
98    .section .init, "ax"\r
99    .code 32\r
100    \r
101    .global ResetHandler\r
102    .global ExitFunction\r
103    .extern main\r
104 /****************************************************************************/\r
105 /*                           Reset handler                                  */\r
106 /****************************************************************************/\r
107 ResetHandler:\r
108 /*\r
109  * Wait for the oscillator is stable\r
110  */   \r
111    nop\r
112    nop\r
113    nop\r
114    nop\r
115    nop\r
116    nop\r
117    nop\r
118    nop\r
119    \r
120 /*\r
121  * Setup STR71X, for more information about the register\r
122  * take a look in the STR71x Microcontroller Reference Manual.\r
123  *\r
124  * Reference is made to: Rev. 6 March 2005\r
125  * \r
126  * 1. Map internal RAM to address 0\r
127  *    In this case, we are running always in the RAM\r
128  *    this make no sence. But if we are in flash, we\r
129  *    can copy the interrupt vectors into the ram and\r
130  *    switch to RAM mode.\r
131  *\r
132  * 2. Setup the PLL, the eval board HITEX STR7 is equipped\r
133  *    with an external 16MHz oscillator. We want:\r
134  *\r
135  *    RCLK:  32MHz = (CLK2 * 16) / 4\r
136  *    MCLK:  32Mhz\r
137  *    PCLK1: 32MHz\r
138  *    PCLK2: 32MHz\r
139  *\r
140  */   \r
141  \r
142    /* \r
143     * 1. Map RAM to the boot memory 0x00000000\r
144     */\r
145    ldr   r0, =PRCCU_BASE\r
146    ldr   r1, =0x01C2          \r
147    str   r1, [r0, #PCU_BOOTCR] \r
148    \r
149    \r
150    /*\r
151     * 2. Setup PLL start\r
152     */\r
153    \r
154    /* Set the prescaling factor for APB and APB1 group */\r
155    ldr   r0, =PRCCU_BASE\r
156    ldr   r1, =0x0000             /* no prescaling PCLKx = RCLK */          \r
157    str   r1, [r0, #PCU_PDIVR] \r
158 \r
159    /* Set the prescaling factor for the Main System Clock MCLK */\r
160    ldr   r0, =PRCCU_BASE\r
161    ldr   r1, =0x0000             /* no prescaling MCLK = RCLK\r
162    str   r1, [r0, #PCU_MDIVR] \r
163    \r
164    /* Configure the PLL1 ( * 16 , / 4 ) */\r
165    ldr   r0, =PRCCU_BASE\r
166    ldr   r1, =0x0073          \r
167    str   r1, [r0, #RCCU_PLL1CR]        \r
168 \r
169    /* Check if the PLL is locked */\r
170 pll_lock_loop:\r
171    ldr   r1, [r0, #RCCU_CFR]\r
172    tst   r1, #0x0002\r
173    beq   pll_lock_loop\r
174    \r
175    /*  Select PLL1_Output as RCLK clock */\r
176    ldr   r0, =PRCCU_BASE\r
177    ldr   r1, =0x8009          \r
178    str   r1, [r0, #RCCU_CFR]        \r
179    \r
180    /*\r
181     * Setup PLL end\r
182     */\r
183     \r
184     \r
185    /*\r
186     * Setup a stack for each mode\r
187     */    \r
188    msr   CPSR_c, #ARM_MODE_UNDEF | I_BIT | F_BIT   /* Undefined Instruction Mode */     \r
189    ldr   sp, =__stack_und_end__\r
190    \r
191    msr   CPSR_c, #ARM_MODE_ABORT | I_BIT | F_BIT   /* Abort Mode */\r
192    ldr   sp, =__stack_abt_end__\r
193    \r
194    msr   CPSR_c, #ARM_MODE_FIQ | I_BIT | F_BIT     /* FIQ Mode */   \r
195    ldr   sp, =__stack_fiq_end__\r
196    \r
197    msr   CPSR_c, #ARM_MODE_IRQ | I_BIT | F_BIT     /* IRQ Mode */   \r
198    ldr   sp, =__stack_irq_end__\r
199    \r
200    msr   CPSR_c, #ARM_MODE_SVC | I_BIT | F_BIT     /* Supervisor Mode */\r
201    ldr   sp, =__stack_svc_end__\r
202 \r
203    \r
204    /*\r
205     * Now init all the sections\r
206     */\r
207 \r
208 \r
209    /* \r
210     * Relocate .data section (Copy from ROM to RAM) \r
211     */\r
212          ldr   r1, =_etext\r
213          ldr   r2, =__data_start\r
214          ldr   r3, =_edata\r
215 LoopRel:\r
216          cmp   r2, r3\r
217          ldrlo r0, [r1], #4\r
218          strlo r0, [r2], #4\r
219          blo   LoopRel\r
220 \r
221 \r
222    /* \r
223     * Clear .bss section (Zero init) \r
224     */\r
225          mov   r0, #0\r
226          ldr   r1, =__bss_start__\r
227          ldr   r2, =__bss_end__\r
228 LoopZI:\r
229          cmp   r1, r2\r
230          strlo r0, [r1], #4\r
231          blo   LoopZI\r
232 \r
233                 \r
234    /* \r
235     * Call C++ constructors \r
236     */\r
237          ldr     r0, =__ctors_start__\r
238          ldr     r1, =__ctors_end__\r
239 ctor_loop:\r
240          cmp     r0, r1\r
241          beq     ctor_end\r
242          ldr     r2, [r0], #4\r
243          stmfd sp!, {r0-r1}\r
244          mov     lr, pc\r
245          mov     pc, r2\r
246          ldmfd sp!, {r0-r1}\r
247          b               ctor_loop\r
248 ctor_end:\r
249    \r
250    \r
251    /*\r
252     * Jump to main\r
253     */\r
254    mrs   r0, cpsr\r
255    bic   r0, r0, #I_BIT | F_BIT     /* Enable FIQ and IRQ interrupt */\r
256    msr   cpsr, r0\r
257    \r
258    mov   r0, #0 /* No arguments */\r
259    mov   r1, #0 /* No arguments */\r
260    ldr   r2, =main\r
261    mov   lr, pc\r
262    bx    r2     /* And jump... */\r
263                        \r
264 ExitFunction:\r
265    nop\r
266    nop\r
267    nop\r
268    b ExitFunction   \r
269    \r
270 \r
271 /****************************************************************************/\r
272 /*                         Default interrupt handler                        */\r
273 /****************************************************************************/\r
274 \r
275 UndefHandler:\r
276    b UndefHandler\r
277    \r
278 SWIHandler:\r
279    b SWIHandler\r
280 \r
281 PAbortHandler:\r
282    b PAbortHandler\r
283 \r
284 DAbortHandler:\r
285    b DAbortHandler\r
286    \r
287 IRQHandler:\r
288    b IRQHandler\r
289    \r
290 FIQHandler:\r
291    b FIQHandler\r
292    \r
293    .weak ExitFunction\r
294    .weak UndefHandler, PAbortHandler, DAbortHandler\r
295    .weak IRQHandler, FIQHandler\r
296 \r
297    .ltorg\r
298 /*** EOF ***/   \r
299         \r
300 \r