srt0.S revision 1.5 1 1.5 joerg /* $NetBSD: srt0.S,v 1.5 2014/08/07 13:56:57 joerg Exp $ */
2 1.1 scw
3 1.1 scw /*-
4 1.1 scw * Copyright (c) 2002 The NetBSD Foundation, Inc.
5 1.1 scw * All rights reserved.
6 1.1 scw *
7 1.1 scw * This code is derived from software contributed to The NetBSD Foundation
8 1.1 scw * by Steve C. Woodford.
9 1.1 scw *
10 1.1 scw * Redistribution and use in source and binary forms, with or without
11 1.1 scw * modification, are permitted provided that the following conditions
12 1.1 scw * are met:
13 1.1 scw * 1. Redistributions of source code must retain the above copyright
14 1.1 scw * notice, this list of conditions and the following disclaimer.
15 1.1 scw * 2. Redistributions in binary form must reproduce the above copyright
16 1.1 scw * notice, this list of conditions and the following disclaimer in the
17 1.1 scw * documentation and/or other materials provided with the distribution.
18 1.1 scw *
19 1.1 scw * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20 1.1 scw * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 1.1 scw * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 1.1 scw * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23 1.1 scw * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 1.1 scw * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 1.1 scw * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 1.1 scw * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 1.1 scw * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 1.1 scw * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 1.1 scw * POSSIBILITY OF SUCH DAMAGE.
30 1.1 scw */
31 1.1 scw
32 1.1 scw #include <machine/asm.h>
33 1.1 scw #include <machine/psl.h>
34 1.1 scw #include <powerpc/spr.h>
35 1.3 matt #include <powerpc/oea/spr.h>
36 1.1 scw
37 1.1 scw #define STACK_SIZE 8192
38 1.1 scw
39 1.1 scw /*
40 1.1 scw * The main entry point when loaded by PPC-Bug.
41 1.1 scw *
42 1.1 scw * There are two possible entry conditions here:
43 1.1 scw *
44 1.1 scw * 1) We were booted in `PReP' mode, either from disk or the network.
45 1.1 scw * In this case, we have no control over the load address so we
46 1.1 scw * have to relocate ourselves to the appropriate place.
47 1.1 scw * The firmware passes us the following registers:
48 1.1 scw *
49 1.4 he * %r1 -> Temporary stack
50 1.4 he * %r3 -> Residual Data
51 1.4 he * %r4 -> The address we were loaded to
52 1.4 he * %r5 -> Zero
53 1.1 scw *
54 1.1 scw * 2) We were booted over the network in Non-PReP mode. In this case,
55 1.1 scw * the load address is usually set using PPC-Bug's "niot" command,
56 1.1 scw * but we won't depend on it so relocation may be required. The
57 1.1 scw * firmware passes us the following registers:
58 1.1 scw *
59 1.4 he * %r1 -> Temporary stack
60 1.4 he * %r3 -> CLUN of the network device we booted from
61 1.4 he * %r4 -> DLUN of the network device we booted from
62 1.4 he * %r5 -> Non-zero
63 1.4 he * %r6 -> Base address of network device
64 1.4 he * %r7 -> Execution address of loaded program
65 1.4 he * %r8 -> Address of IP-address data structure
66 1.4 he * %r9 -> Pointer to start of filename string
67 1.4 he * %r10 -> Pointer to end+1 of filename string
68 1.4 he * %r11 -> Pointer to start of argument string
69 1.4 he * %r12 -> Pointer to end+1 of argument string
70 1.1 scw *
71 1.1 scw * The obvious way to distinguish between the two boot modes is by
72 1.4 he * checking the value of %r5.
73 1.1 scw */
74 1.1 scw ENTRY(_start)
75 1.1 scw bl 1f
76 1.4 he 1: xor %r0,%r0,%r0
77 1.1 scw
78 1.1 scw /* First, switch off Instruction and Data caches. */
79 1.4 he mfspr %r13,SPR_HID0
80 1.4 he LDCONST(%r14, HID0_DCE|HID0_ICE)
81 1.4 he andc %r13,%r13,%r14
82 1.1 scw sync
83 1.4 he mtspr SPR_HID0,%r13
84 1.1 scw
85 1.1 scw
86 1.1 scw /*
87 1.1 scw * All registers now available. Let's see if we need to relocate
88 1.1 scw */
89 1.4 he LDCONST(%r13,_C_LABEL(_start)) /* Where we'd like to be */
90 1.4 he LDCONST(%r14,_C_LABEL(edata)) /* End of data section */
91 1.4 he LDCONST(%r15,0x3)
92 1.4 he add %r14,%r14,%r15
93 1.4 he andc %r14,%r14,%r15 /* Rounded up to the nearest 32-bits */
94 1.4 he sub %r15,%r14,%r13 /* Our size, in bytes */
95 1.4 he mflr %r16 /* Get address we were loaded to */
96 1.4 he subi %r16,%r16,0x4 /* Correct for branch */
97 1.5 joerg cmpw %r13,%r16 /* Do we need to relocate? */
98 1.1 scw beq _ASM_LABEL(clrbss) /* No relocation necessary */
99 1.4 he li %r17,0x4
100 1.1 scw bgt 1f /* Relocate using forward copy? */
101 1.1 scw
102 1.1 scw /* Nope. Need to copy in reverse in case of overlap */
103 1.4 he mr %r13,%r14 /* dest -> end */
104 1.4 he add %r16,%r16,%r15 /* src + size */
105 1.4 he subi %r17,%r17,0x8 /* Increment is -4 */
106 1.1 scw
107 1.1 scw /*
108 1.1 scw * Do the relocation
109 1.4 he * %r13 -> dest
110 1.4 he * %r15 -> number of bytes
111 1.4 he * %r16 -> src
112 1.4 he * %r17 -> Increment (+4 or -4)
113 1.1 scw */
114 1.4 he 1: srwi %r15,%r15,0x2 /* Convert length to 32-bit words */
115 1.4 he mtctr %r15 /* Save in counter register */
116 1.1 scw
117 1.4 he 2: lwz %r15,0(%r16)
118 1.4 he stw %r15,0(%r13)
119 1.4 he add %r16,%r16,%r17
120 1.4 he add %r13,%r13,%r17
121 1.1 scw bdnz 2b
122 1.1 scw
123 1.1 scw /* Now do an absolute jump to the relocated code */
124 1.4 he LDCONST(%r13,_ASM_LABEL(clrbss))
125 1.4 he mtlr %r13
126 1.1 scw blr
127 1.1 scw
128 1.1 scw ASENTRY(clrbss)
129 1.4 he LDCONST(%r13,_C_LABEL(edata)) /* End of the data section */
130 1.4 he LDCONST(%r14,_C_LABEL(end)) /* End of BSS */
131 1.4 he LDCONST(%r15,0x3)
132 1.4 he add %r14,%r14,%r15
133 1.4 he andc %r14,%r14,%r15 /* Round-up end of BSS to 32-bits */
134 1.4 he sub %r15,%r14,%r13 /* r15 == length of BSS */
135 1.4 he srwi %r15,%r15,0x2
136 1.4 he mtctr %r15 /* CTR == # of 32-bit words in BSS */
137 1.4 he 1: stw %r0,0(%r13) /* Clear BSS */
138 1.4 he addi %r13,%r13,4
139 1.1 scw bdnz 1b
140 1.1 scw
141 1.1 scw /* Fix up our own stack */
142 1.4 he LDCONST(%r1,stack)
143 1.4 he addi %r1,%r1,STACK_SIZE-0x10
144 1.4 he LDCONST(%r13,0x0f)
145 1.4 he andc %r1,%r1,%r13
146 1.1 scw
147 1.1 scw /*
148 1.1 scw * Copy the arguments passed in from Bug into bug_bootinfo
149 1.1 scw *
150 1.1 scw * See bugsyscalls.h for details.
151 1.1 scw */
152 1.4 he LDCONST(%r13,_C_LABEL(bug_bootinfo))
153 1.4 he stw %r5,0x00(%r13)
154 1.4 he stw %r3,0x04(%r13)
155 1.4 he stw %r4,0x08(%r13)
156 1.4 he stw %r6,0x0c(%r13)
157 1.4 he stw %r7,0x10(%r13)
158 1.4 he stw %r8,0x14(%r13)
159 1.4 he stw %r9,0x18(%r13)
160 1.4 he stw %r10,0x1c(%r13)
161 1.4 he stw %r11,0x20(%r13)
162 1.4 he stw %r12,0x24(%r13)
163 1.1 scw
164 1.4 he mr %r3,%r13
165 1.1 scw bl _C_LABEL(main) /* void main(void) */
166 1.1 scw /* FALLTHROUGH */
167 1.1 scw
168 1.1 scw /*
169 1.1 scw * Return to the debugger, either because main() returned or via panic().
170 1.1 scw */
171 1.1 scw ENTRY(_rtt)
172 1.4 he addi %r10,0,0x0063
173 1.1 scw sc
174 1.1 scw 1: nop
175 1.1 scw b 1b
176 1.1 scw
177 1.1 scw /*
178 1.1 scw * C code runs on this stack.
179 1.1 scw */
180 1.1 scw .comm stack,STACK_SIZE,4
181 1.1 scw .comm errno,4,4
182 1.1 scw .comm debug,4,4
183