source: rtems/bsps/powerpc/gen83xx/start/start.S @ fe8b4b6c

Last change on this file since fe8b4b6c was fe8b4b6c, checked in by Joel Sherrill <joel@…>, on 07/11/22 at 22:28:07

bsps/powerpc/83xx: Change license to BSD-2

Updates #3053.

  • Property mode set to 100644
File size: 13.0 KB
Line 
1/* SPDX-License-Identifier: BSD-2-Clause */
2
3/*
4 * RTEMS generic MPC83xx BSP
5 *
6 * This file contains the startup assembly code.
7 */
8
9/*
10 * Copyright (c) 2007 embedded brains GmbH. All rights reserved.
11 *
12 * Redistribution and use in source and binary forms, with or without
13 * modification, are permitted provided that the following conditions
14 * are met:
15 * 1. Redistributions of source code must retain the above copyright
16 *    notice, this list of conditions and the following disclaimer.
17 * 2. Redistributions in binary form must reproduce the above copyright
18 *    notice, this list of conditions and the following disclaimer in the
19 *    documentation and/or other materials provided with the distribution.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
22 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
25 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
26 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
27 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
28 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
29 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31 * POSSIBILITY OF SUCH DAMAGE.
32 */
33
34#include <libcpu/powerpc-utility.h>
35#include <rtems/powerpc/cache.h>
36#include <bsp.h>
37#include <mpc83xx/mpc83xx.h>
38
39.macro SET_IMM_REGW base, reg2, offset, value
40        LA \reg2, \value
41        stw \reg2,\offset(\base)
42.endm
43
44#define REP8(l) l ; l; l; l; l; l; l; l;
45
46.extern boot_card
47.extern MBAR
48
49#if defined(RESET_CONF_WRD_L)
50.section ".resconf","ax"
51PUBLIC_VAR (reset_conf_words)
52reset_conf_words:
53        REP8( .byte ((RESET_CONF_WRD_L >> 24) & 0xff))
54        REP8( .byte ((RESET_CONF_WRD_L >> 16) & 0xff))
55        REP8( .byte ((RESET_CONF_WRD_L >>  8) & 0xff))
56        REP8( .byte ((RESET_CONF_WRD_L >>  0) & 0xff))
57
58        REP8( .byte ((RESET_CONF_WRD_H >> 24) & 0xff))
59        REP8( .byte ((RESET_CONF_WRD_H >> 16) & 0xff))
60        REP8( .byte ((RESET_CONF_WRD_H >>  8) & 0xff))
61        REP8( .byte ((RESET_CONF_WRD_H >>  0) & 0xff))
62#endif
63
64.section ".vectors","ax"
65PUBLIC_VAR (reset_vec)
66reset_vec:
67        bl rom_entry
68
69.section ".bsp_start_text", "ax"
70PUBLIC_VAR (_start)
71_start:
72        /* Reset time base */
73        li      r0, 0
74        mtspr   TBWU, r0
75        mtspr   TBWL, r0
76
77#ifdef HAS_UBOOT
78        mr      r14, r3
79#endif /* HAS_UBOOT */
80
81        /*
82         * basic CPU setup:
83         * init MSR
84         */
85        mfmsr   r30
86        SETBITS r30, r29, MSR_ME|MSR_RI
87        CLRBITS r30, r29, MSR_IP|MSR_EE
88        mtmsr   r30                             /* Set RI/ME, Clr EE in MSR */
89
90        b start_rom_skip
91
92PUBLIC_VAR (rom_entry)
93rom_entry:
94        /*
95         * basic CPU setup:
96         * init MSR
97         */
98        mfmsr   r30
99        SETBITS r30, r29, MSR_ME|MSR_RI
100        CLRBITS r30, r29, MSR_IP|MSR_EE
101        mtmsr   r30                             /* Set RI/ME, Clr EE in MSR */
102
103        /*
104         * ROM startup: remap IMMR to 0xE0000000
105         * use special sequence from MPC8349EA RM Rev 1, 5.2.4.1.1 "Updating IMMRBAR"
106         */
107        LWI  r30,IMMRBAR_DEFAULT
108        LWI  r31,IMMRBAR
109        lwz  r29,0(r30)
110        stw  r31,0(r30)
111#if 0
112        lwz  r29,0(r28) /* read from ROM... */
113#endif
114        isync
115        lwz  r29,0(r31) /* read from IMMRBAR... */
116        isync
117        /*
118         * NOTE:         now r31 points to onchip registers
119        */
120        /*
121         * we start from 0x100, so ROM is currently mapped to
122         * 0x00000000..
123         * in the next step, ROM will be remapped to its final location
124         * at 0xfe000000... (using LBLAWBAR1 with LBLAWBAR0 value)
125         * and we jump to that location.
126         * then we remove the ROM mapping to zero
127         */
128#ifdef LBLAWBAR0_VAL
129        SET_IMM_REGW r31,r30,LBLAWBAR1_OFF,LBLAWBAR0_VAL
130#endif
131#ifdef LBLAWAR0_VAL
132        SET_IMM_REGW r31,r30,LBLAWAR1_OFF,LBLAWAR0_VAL
133#endif
134
135
136        /*
137         * ROM startup: jump to code final ROM location
138         */
139        LA      r20, bsp_rom_start /* ROM-RAM reloc in r20 */
140        LA      r29, start_code_in_rom /* get compile time addr of label */
141        add     r29,r20,r29    /* compute exec address */
142        mtlr    r29
143        blr                     /* now further execution in upper ROM */
144
145start_code_in_rom:
146
147#ifdef LBLAWBAR0_VAL
148        SET_IMM_REGW r31,r30,LBLAWBAR0_OFF,LBLAWBAR0_VAL
149#endif
150#ifdef LBLAWAR0_VAL
151        SET_IMM_REGW r31,r30,LBLAWAR0_OFF,LBLAWAR0_VAL
152#endif
153
154/*
155 * Local access window 1 is a special case since we used it for a temporary
156 * mapping.  If we do not use it then restore the reset value.
157 */
158#ifdef LBLAWBAR1_VAL
159        SET_IMM_REGW r31,r30,LBLAWBAR1_OFF,LBLAWBAR1_VAL
160#else
161        SET_IMM_REGW r31,r30,LBLAWBAR1_OFF,0
162#endif
163#ifdef LBLAWAR1_VAL
164        SET_IMM_REGW r31,r30,LBLAWAR1_OFF,LBLAWAR1_VAL
165#else
166        SET_IMM_REGW r31,r30,LBLAWAR1_OFF,0
167#endif
168
169#ifdef LBLAWBAR2_VAL
170        SET_IMM_REGW r31,r30,LBLAWBAR2_OFF,LBLAWBAR2_VAL
171#endif
172#ifdef LBLAWAR2_VAL
173        SET_IMM_REGW r31,r30,LBLAWAR2_OFF,LBLAWAR2_VAL
174#endif
175#ifdef LBLAWBAR3_VAL
176        SET_IMM_REGW r31,r30,LBLAWBAR3_OFF,LBLAWBAR3_VAL
177#endif
178#ifdef LBLAWAR3_VAL
179        SET_IMM_REGW r31,r30,LBLAWAR3_OFF,LBLAWAR3_VAL
180#endif
181        /*
182         * ROM startup: init bus system
183         */
184#ifdef BR0_VAL
185        SET_IMM_REGW r31,r30,BR0_OFF,BR0_VAL
186#endif
187#ifdef OR0_VAL
188        SET_IMM_REGW r31,r30,OR0_OFF,OR0_VAL
189#endif
190#ifdef BR1_VAL
191        SET_IMM_REGW r31,r30,BR1_OFF,BR1_VAL
192#endif
193#ifdef OR1_VAL
194        SET_IMM_REGW r31,r30,OR1_OFF,OR1_VAL
195#endif
196#ifdef BR2_VAL
197        SET_IMM_REGW r31,r30,BR2_OFF,BR2_VAL
198#endif
199#ifdef OR2_VAL
200        SET_IMM_REGW r31,r30,OR2_OFF,OR2_VAL
201#endif
202#ifdef BR3_VAL
203        SET_IMM_REGW r31,r30,BR3_OFF,BR3_VAL
204#endif
205#ifdef OR3_VAL
206        SET_IMM_REGW r31,r30,OR3_OFF,OR3_VAL
207#endif
208#ifdef BR4_VAL
209        SET_IMM_REGW r31,r30,BR4_OFF,BR4_VAL
210#endif
211#ifdef OR4_VAL
212        SET_IMM_REGW r31,r30,OR4_OFF,OR4_VAL
213#endif
214#ifdef BR5_VAL
215        SET_IMM_REGW r31,r30,BR5_OFF,BR5_VAL
216#endif
217#ifdef OR5_VAL
218        SET_IMM_REGW r31,r30,OR5_OFF,OR5_VAL
219#endif
220        /*
221         * ROM startup: init SDRAM access window
222         */
223#ifdef DDRLAWBAR0_VAL
224        SET_IMM_REGW r31,r30,DDRLAWBAR0_OFF,DDRLAWBAR0_VAL
225#endif
226#ifdef DDRLAWAR0_VAL
227        SET_IMM_REGW r31,r30,DDRLAWAR0_OFF,DDRLAWAR0_VAL
228#endif
229#ifdef DDRLAWBAR1_VAL
230        SET_IMM_REGW r31,r30,DDRLAWBAR1_OFF,DDRLAWBAR1_VAL
231#endif
232#ifdef DDRLAWAR1_VAL
233        SET_IMM_REGW r31,r30,DDRLAWAR1_OFF,DDRLAWAR1_VAL
234#endif
235        /*
236         * ROM startup: init refresh interval
237         */
238#ifdef MRPTR_VAL
239        SET_IMM_REGW r31,r30,MRPTR_OFF,MRPTR_VAL
240#endif
241        /*
242         * ROM startup: init SDRAM
243         */
244#ifdef LSRT_VAL
245        SET_IMM_REGW r31,r30, LSRT_OFF, LSRT_VAL
246#endif
247#ifdef LSDMR_VAL
248        SET_IMM_REGW r31,r30, LSDMR_OFF, LSDMR_VAL
249#endif
250#ifdef CS0_BNDS_VAL
251        SET_IMM_REGW r31,r30,CS0_BNDS_OFF,CS0_BNDS_VAL
252#endif
253#ifdef CS1_BNDS_VAL
254        SET_IMM_REGW r31,r30,CS1_BNDS_OFF,CS1_BNDS_VAL
255#endif
256#ifdef CS2_BNDS_VAL
257        SET_IMM_REGW r31,r30,CS2_BNDS_OFF,CS2_BNDS_VAL
258#endif
259#ifdef CS3_BNDS_VAL
260        SET_IMM_REGW r31,r30,CS3_BNDS_OFF,CS3_BNDS_VAL
261#endif
262#ifdef CS0_CONFIG_VAL
263        SET_IMM_REGW r31,r30,CS0_CONFIG_OFF,CS0_CONFIG_VAL
264#endif
265#ifdef CS1_CONFIG_VAL
266        SET_IMM_REGW r31,r30,CS1_CONFIG_OFF,CS1_CONFIG_VAL
267#endif
268#ifdef CS2_CONFIG_VAL
269        SET_IMM_REGW r31,r30,CS2_CONFIG_OFF,CS2_CONFIG_VAL
270#endif
271#ifdef CS3_CONFIG_VAL
272        SET_IMM_REGW r31,r30,CS3_CONFIG_OFF,CS3_CONFIG_VAL
273#endif
274#ifdef TIMING_CFG_3_VAL
275        SET_IMM_REGW r31,r30,TIMING_CFG_3_OFF,TIMING_CFG_3_VAL
276#endif
277#ifdef TIMING_CFG_0_VAL
278        SET_IMM_REGW r31,r30,TIMING_CFG_0_OFF,TIMING_CFG_0_VAL
279#endif
280#ifdef TIMING_CFG_1_VAL
281        SET_IMM_REGW r31,r30,TIMING_CFG_1_OFF,TIMING_CFG_1_VAL
282#endif
283#ifdef TIMING_CFG_2_VAL
284        SET_IMM_REGW r31,r30,TIMING_CFG_2_OFF,TIMING_CFG_2_VAL
285#endif
286#ifdef DDRCDR_VAL
287        SET_IMM_REGW r31,r30,DDRCDR_OFF,DDRCDR_VAL
288#endif
289#ifdef DDR_SDRAM_CFG_2_VAL
290        SET_IMM_REGW r31,r30,DDR_SDRAM_CFG_2_OFF,DDR_SDRAM_CFG_2_VAL
291#endif
292#ifdef DDR_SDRAM_MODE_VAL
293        SET_IMM_REGW r31,r30,DDR_SDRAM_MODE_OFF,DDR_SDRAM_MODE_VAL
294#endif
295#ifdef DDR_SDRAM_MODE_2_VAL
296        SET_IMM_REGW r31,r30,DDR_SDRAM_MODE_2_OFF,DDR_SDRAM_MODE_2_VAL
297#endif
298#ifdef DDR_SDRAM_MD_CNTL_VAL
299        SET_IMM_REGW r31,r30,DDR_SDRAM_MD_CNTL_OFF,DDR_SDRAM_MD_CNTL_VAL
300#endif
301#ifdef DDR_SDRAM_MD_ITVL_VAL
302        SET_IMM_REGW r31,r30,DDR_SDRAM_MD_ITVL_OFF,DDR_SDRAM_MD_ITVL_VAL
303#endif
304#ifdef DDR_SDRAM_CLK_CNTL_VAL
305        SET_IMM_REGW r31,r30,DDR_SDRAM_CLK_CNTL_OFF,DDR_SDRAM_CLK_CNTL_VAL
306#endif
307#ifdef DDR_SDRAM_CFG_2_VAL
308        SET_IMM_REGW r31,r30,DDR_SDRAM_CFG_2_OFF,DDR_SDRAM_CFG_2_VAL|DDR_SDRAM_CFG_2_D_INIT
309#endif
310
311#ifdef DDR_ERR_DISABLE_VAL
312        /*
313         * disable detect of RAM errors
314         */
315        SET_IMM_REGW r31,r30,DDR_ERR_DISABLE_OFF,DDR_ERR_DISABLE_VAL
316#endif
317#ifdef DDR_SDRAM_DATA_INIT_VAL
318        /*
319         * set this value to initialize memory
320         */
321        SET_IMM_REGW r31,r30,DDR_SDRAM_DATA_INIT_OFF,DDR_SDRAM_DATA_INIT_VAL
322#endif
323#ifdef DDR_SDRAM_INIT_ADDR_VAL
324        SET_IMM_REGW r31,r30,DDR_SDRAM_INIT_ADDR_OFF,DDR_SDRAM_INIT_ADDR_VAL
325#endif
326#ifdef DDR_SDRAM_CFG_VAL
327        /*
328         * config DDR SDRAM
329         */
330        SET_IMM_REGW r31,r30,DDR_SDRAM_CFG_OFF,DDR_SDRAM_CFG_VAL & ~DDR_SDRAM_CFG_MEM_EN
331        /*
332         * FIXME: wait 200us
333         */
334        /*
335         * enable  DDR SDRAM
336         */
337        SET_IMM_REGW r31,r30,DDR_SDRAM_CFG_OFF,DDR_SDRAM_CFG_VAL | DDR_SDRAM_CFG_MEM_EN
338        /*
339         * wait, until DDR_SDRAM_CFG_2_D_INIT is cleared
340         */
3411:      lwz r30,DDR_SDRAM_CFG_2_OFF(r31)
342        andi. r30,r30,DDR_SDRAM_CFG_2_D_INIT
343        bne 1b
344#endif
345#ifdef DDR_ERR_DISABLE_VAL2
346        /*
347         * enable detect of some RAM errors
348         */
349        SET_IMM_REGW r31,r30,DDR_ERR_DISABLE_OFF,DDR_ERR_DISABLE_VAL2
350#endif
351#ifdef DDR_SDRAM_INTERVAL_VAL
352        /*
353         * set the refresh interval
354         */
355        SET_IMM_REGW r31,r30,DDR_SDRAM_INTERVAL_OFF,DDR_SDRAM_INTERVAL_VAL
356#endif
357start_rom_skip:
358        /*
359         * determine current execution address offset
360         */
361        bl start_rom_skip1
362start_rom_skip1:
363        mflr r20
364        LA   r30,start_rom_skip1
365        sub. r20,r20,r30
366        /*
367         * execution address offset == 0?
368         * then do not relocate code and data
369         */
370        beq  start_code_in_ram
371        /*
372         * ROM or relocatable startup: copy startup code to SDRAM
373         */
374        /* get start address of start section in RAM */
375        LA      r29, bsp_section_start_begin
376        /* get start address of start section in ROM (add reloc offset) */
377        add     r30, r20, r29
378        /* get size of startup code */
379        LA      r28, bsp_section_start_end
380        sub     28,r28,r29
381        /* copy startup code from ROM to RAM location */
382        bl      copy_image
383
384        /*
385         * ROM startup: jump to code copy in  SDRAM
386         */
387        /* get compile time address of label */
388        LA      r29, copy_rest_of_text
389        mtlr    r29
390        blr                     /* now further execution RAM */
391copy_rest_of_text:
392        LWI  r31,IMMRBAR
393#ifdef LCRR_VAL
394        SET_IMM_REGW r31,r30,LCRR_OFF,LCRR_VAL
395#endif
396        /*
397         * ROM or relocatable startup: copy rest of code to SDRAM
398         */
399        /* get start address of rest of loadable sections in RAM */
400        LA      r29, bsp_section_text_begin
401        /* get start address of loadable sections in ROM (add reloc offset) */
402        add     r30, r20, r29
403        /* get size of rest of loadable sections */
404        LA      r28, bsp_section_data_end
405        sub     r28,r28,r29
406        bl      copy_image      /* copy text section from ROM to RAM location */
407
408start_code_in_ram:
409
410        /*
411         * ROM/RAM startup: clear bss in SDRAM
412         */
413        LA      r3, bsp_section_sbss_begin  /* get start address of bss section */
414        LA      r4, bsp_section_bss_end     /* get end address of bss section */
415        sub     r4, r4, r3                  /* get size of bss section */
416        bl      mpc83xx_zero_4              /* Clear the bss section */
417
418#ifdef HAS_UBOOT
419        mr      r3, r14
420        bl      bsp_uboot_copy_board_info
421#endif /* HAS_UBOOT */
422
423        /* Read-only small data */
424        LA r2, _SDA2_BASE_
425
426        /* Read-write small data */
427        LA r13, _SDA_BASE_
428
429        /* Clear cmdline */
430        li      r3, 0
431
432        /*
433         * Initialize start stack.  The stacks are statically allocated and
434         * properly aligned.
435         */
436        LA      r1, _ISR_Stack_area_end
437        subi    r1, r1, PPC_DEFAULT_CACHE_LINE_SIZE
438        stw     r3, 0(r1)
439
440        /* Call the first C routine */
441        bl      SYM (boot_card)
442
443twiddle:
444        /* We don't expect to return from boot_card but if we do */
445        /* wait here for watchdog to kick us into hard reset     */
446        b       twiddle
447
448copy_image:
449        cmpwi   r28, 0
450        beqlr
451
452        mr      r27, r28
453        srwi    r28, r28, 2
454        mtctr   r28
455
456        slwi    r28, r28, 2
457        sub     r27, r27, r28                   /* maybe some residual bytes */
458copy_image_word:
459        lswi    r28, r30, 0x04
460
461        stswi   r28, r29, 0x04                  /* do word copy ROM -> RAM */
462
463
464        addi    r30, r30, 0x04                  /* increment source pointer */
465        addi    r29, r29, 0x04                  /* increment destination pointer */
466
467        bdnz    copy_image_word                 /* decrement ctr and branch if not 0 */
468
469        cmpwi   r27, 0x00                       /* copy image finished ? */
470        beq     copy_image_end;
471        mtctr   r27                             /* reload counter for residual bytes */
472copy_image_byte:
473        lswi    r28, r30, 0x01
474
475        stswi   r28, r29, 0x01                  /* do byte copy ROM -> RAM */
476
477
478        addi    r30, r30, 0x01                  /* increment source pointer */
479        addi    r29, r29, 0x01                  /* increment destination pointer */
480
481        bdnz    copy_image_byte                 /* decrement ctr and branch if not 0 */
482
483copy_image_end:
484        blr
485
486
487/**
488 * @fn int mpc83xx_zero_4( void *dest, size_t n)
489 *
490 * @brief Zero all @a n bytes starting at @a dest with 4 byte writes.
491 *
492 * The address @a dest has to be aligned on 4 byte boundaries.  The size @a n
493 * must be evenly divisible by 4.
494 */
495GLOBAL_FUNCTION mpc83xx_zero_4
496        /* Create zero */
497        xor     r0, r0, r0
498
499        /* Set offset */
500        xor     r5, r5, r5
501
502        /* Loop counter for the first bytes up to 16 bytes */
503        rlwinm. r9, r4, 30, 30, 31
504        beq     mpc83xx_zero_4_more
505        mtctr   r9
506
507mpc83xx_zero_4_head:
508
509        stwx    r0, r3, r5
510        addi    r5, r5, 4
511        bdnz    mpc83xx_zero_4_head
512
513mpc83xx_zero_4_more:
514
515        /* More than 16 bytes? */
516        srwi.   r9, r4, 4
517        beqlr
518        mtctr   r9
519
520        /* Set offsets */
521        addi    r6, r5, 4
522        addi    r7, r5, 8
523        addi    r8, r5, 12
524
525mpc83xx_zero_4_tail:
526
527        stwx    r0, r3, r5
528        addi    r5, r5, 16
529        stwx    r0, r3, r6
530        addi    r6, r6, 16
531        stwx    r0, r3, r7
532        addi    r7, r7, 16
533        stwx    r0, r3, r8
534        addi    r8, r8, 16
535        bdnz    mpc83xx_zero_4_tail
536
537        /* Return */
538        blr
Note: See TracBrowser for help on using the repository browser.