source: rtems/c/src/lib/libbsp/powerpc/shared/startup/probeMemEnd.c @ 9b4422a2

4.115
Last change on this file since 9b4422a2 was 9b4422a2, checked in by Joel Sherrill <joel.sherrill@…>, on 05/03/12 at 15:09:24

Remove All CVS Id Strings Possible Using a Script

Script does what is expected and tries to do it as
smartly as possible.

+ remove occurrences of two blank comment lines

next to each other after Id string line removed.

+ remove entire comment blocks which only exited to

contain CVS Ids

+ If the processing left a blank line at the top of

a file, it was removed.

  • Property mode set to 100644
File size: 5.9 KB
Line 
1#include <rtems.h>
2#include <libcpu/spr.h>
3#include <libcpu/cpuIdent.h>
4#include <rtems/bspIo.h>
5
6/*
7 * Authorship
8 * ----------
9 * This software was created by
10 *     Till Straumann <strauman@slac.stanford.edu>, 2005,
11 *         Stanford Linear Accelerator Center, Stanford University.
12 *
13 * Acknowledgement of sponsorship
14 * ------------------------------
15 * This software was produced by
16 *     the Stanford Linear Accelerator Center, Stanford University,
17 *         under Contract DE-AC03-76SFO0515 with the Department of Energy.
18 *
19 * Government disclaimer of liability
20 * ----------------------------------
21 * Neither the United States nor the United States Department of Energy,
22 * nor any of their employees, makes any warranty, express or implied, or
23 * assumes any legal liability or responsibility for the accuracy,
24 * completeness, or usefulness of any data, apparatus, product, or process
25 * disclosed, or represents that its use would not infringe privately owned
26 * rights.
27 *
28 * Stanford disclaimer of liability
29 * --------------------------------
30 * Stanford University makes no representations or warranties, express or
31 * implied, nor assumes any liability for the use of this software.
32 *
33 * Stanford disclaimer of copyright
34 * --------------------------------
35 * Stanford University, owner of the copyright, hereby disclaims its
36 * copyright and all other rights in this software.  Hence, anyone may
37 * freely use it for any purpose without restriction.
38 *
39 * Maintenance of notices
40 * ----------------------
41 * In the interest of clarity regarding the origin and status of this
42 * SLAC software, this and all the preceding Stanford University notices
43 * are to remain affixed to any copy or derivative of this software made
44 * or distributed by the recipient and are to be affixed to any copy of
45 * software made or distributed by the recipient that contains a copy or
46 * derivative of this software.
47 *
48 * ------------------ SLAC Software Notices, Set 4 OTT.002a, 2004 FEB 03
49 */
50
51
52/* Simple memory probing routine
53 *
54 *  - call from MMU-disabled section to avoid having to
55 *        set up mappings.
56 *    NOTE: this implies WIMG = 0011
57 *  - call AFTER image is at its destination and PRIOR
58 *    to setting up the heap or using any memory beyond
59 *    __rtems_end, i.e., the probing algorithm may safely
60 *    tamper with memory > __rtems_end.
61 *  - MUST lock caches since we're gonna hit space with
62 *    no memory attached.
63 *
64 * ASSUMPTIONS:
65 *              o image occupies addresses between 0..__rtems_end
66 *              o memory size is a multiple of 1<<LD_MEM_PROBE_STEP
67 *
68 * CAVEATS:
69 *      o all caches must be disabled or locked (some
70 *        boards really don't like it if you try to
71 *        cache physical addresses with nothing attached)
72 *        and this is highly CPU dependent :-(...
73 *
74 *      - RETURNS size of memory detected in bytes or 0 on
75 *    error.
76 */
77
78/* declare as an array so the compiler doesn't generate
79 * a reloc to .sdata & friends
80 */
81extern uint32_t __rtems_end[];
82
83#ifndef LD_MEM_PROBE_STEP
84#define LD_MEM_PROBE_STEP       (24) /* 16MB */
85#endif
86
87#define TAG 0xfeedcafe
88
89#define __DO_ALIGN(a, s)        (((uint32_t)(a) + (s)-1) & ~((s)-1))
90#define __ALIGN(a)      __DO_ALIGN(a, (1<<LD_MEM_PROBE_STEP))
91
92#define SWITCH_MSR(msr)         \
93        do {                                    \
94        register uint32_t __rr; \
95        asm volatile(                   \
96                "       mtsrr1  %0      \n"     \
97                "   bl 1f               \n"     \
98                "1:     mflr    %0      \n"     \
99                "       addi %0, %0, 1f-1b      \n"\
100                "       mtsrr0  %0      \n"     \
101                "       sync            \n"     \
102                "       rfi                     \n"     \
103                "1:                             \n"     \
104                :"=b&"(__rr)            \
105                :"0"(msr)                       \
106                :"lr","memory"          \
107        );                                              \
108        } while (0)
109
110SPR_RW(L2CR)
111SPR_RW(L3CR)
112SPR_RO(PPC_PVR)
113SPR_RW(HID0)
114
115
116/* Shouldn't matter if the caches are enabled or not... */
117
118/* FIXME: This should go into libcpu, really... */
119int
120CPU_lockUnlockCaches(register int doLock)
121{
122register uint32_t v, x;
123        if ( _read_MSR() & MSR_VE ) {
124#define DSSALL  0x7e00066c  /* dssall opcode */
125        __asm__ volatile("  .long %0"::"i"(DSSALL));
126#undef  DSSALL
127        }
128        asm volatile("sync");
129        switch ( _read_PPC_PVR()>>16 ) {
130                default:                printk(__FILE__" CPU_lockUnlockCaches(): unknown CPU (PVR = 0x%08x)\n",_read_PPC_PVR());
131                                                return -1;
132                case PPC_750:   printk("CPU_lockUnlockCaches(): Can't lock L2 on a mpc750, sorry :-(\n");
133                                                return -2;      /* cannot lock L2 :-( */
134                case PPC_7455:
135                case PPC_7457:
136                                                v = _read_L3CR();
137                                                x = 1<<(31-9);
138                                                v = doLock ? v | x : v & ~x;
139                                                _write_L3CR(v);
140
141                                                v = _read_L2CR();
142                                                x = 1<<(31-11);
143                                                v = doLock ? v | x : v & ~x;
144                                                _write_L2CR(v);
145                                break;
146
147                case PPC_7400:
148                                                v = _read_L2CR();
149                                                x = 1<<(31-21);
150                                                v = doLock ? v | x : v & ~x;
151                                                _write_L2CR(v);
152                                break;
153                case PPC_603:
154                case PPC_604:
155                case PPC_604e:
156                                break;
157        }
158
159        v = _read_HID0();
160        x = 1<<(31-19);
161        v = doLock ? v | x : v & ~x;
162        _write_HID0(v);
163        asm volatile("sync":::"memory");
164        return 0;
165}
166
167uint32_t
168probeMemoryEnd(void)
169{
170register volatile uint32_t *probe;
171register          uint32_t scratch;
172register          uint32_t tag = TAG;
173register          uint32_t flags;
174
175        probe = (volatile uint32_t *)__ALIGN(__rtems_end);
176
177        /* Start with some checks. We avoid using any services
178         * such as 'printk' so we can run at a very early stage.
179         * Also, we *try* to avoid to really rely on the memory
180         * being unused by restoring the probed locations and
181         * keeping everything in registers. Hence we could
182         * even probe our own stack :-)
183         */
184
185        if ( CPU_lockUnlockCaches(1) )
186                return 0;
187
188        _CPU_MSR_GET(flags);
189
190        SWITCH_MSR( flags & ~(MSR_EE|MSR_DR|MSR_IR) );
191
192        for ( ; (uint32_t)probe ;  probe += (1<<LD_MEM_PROBE_STEP)/sizeof(*probe) ) {
193
194                /* see if by chance our tag is already there */
195                if ( tag == (scratch = *probe) ) {
196                        /* try another tag */
197                        tag = ~tag;
198                }
199                *probe = tag;
200
201                /* make sure it's written out */
202                asm volatile ("sync":::"memory");
203
204                /* try to read back */
205                if ( tag != *probe ) {
206                                break;
207                }
208                /* restore */
209                *probe = scratch;
210                /* make sure the icache is not contaminated */
211                asm volatile ("sync; icbi 0, %0"::"r"(probe):"memory");
212        }
213
214        SWITCH_MSR(flags);
215
216        CPU_lockUnlockCaches(0);
217
218        return (uint32_t) probe;
219}
Note: See TracBrowser for help on using the repository browser.