Merge branch 'x86-mm-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git...
[sfrench/cifs-2.6.git] / arch / xtensa / boot / boot-redboot / bootstrap.S
1 /* SPDX-License-Identifier: GPL-2.0 */
2 #include <variant/core.h>
3 #include <asm/regs.h>
4 #include <asm/asmmacro.h>
5 #include <asm/cacheasm.h>
6         /*
7          * RB-Data: RedBoot data/bss
8          * P:       Boot-Parameters
9          * L:       Kernel-Loader
10          *
11          * The Linux-Kernel image including the loader must be loaded
12          * to a position so that the kernel and the boot parameters
13          * can fit in the space before the load address.
14          *  ______________________________________________________
15          * |_RB-Data_|_P_|__________|_L_|___Linux-Kernel___|______|
16          *                          ^
17          *                          ^ Load address
18          *  ______________________________________________________
19          * |___Linux-Kernel___|_P_|_L_|___________________________|
20          *
21          * The loader copies the parameter to the position that will
22          * be the end of the kernel and itself to the end of the
23          * parameter list.
24          */
25
26 /* Make sure we have enough space for the 'uncompressor' */
27
28 #define STACK_SIZE 32768
29 #define HEAP_SIZE (131072*4)
30
31         # a2: Parameter list
32         # a3: Size of parameter list
33
34         .section .start, "ax"
35
36         .globl __start
37         /* this must be the first byte of the loader! */
38 __start:
39         entry   sp, 32          # we do not intend to return
40         _call0  _start
41 __start_a0:
42         .align 4
43
44         .section .text, "ax"
45         .literal_position
46         .begin literal_prefix .text
47
48         /* put literals in here! */
49
50         .globl _start
51 _start:
52
53         /* 'reset' window registers */
54
55         movi    a4, 1
56         wsr     a4, ps
57         rsync
58
59         rsr     a5, windowbase
60         ssl     a5
61         sll     a4, a4
62         wsr     a4, windowstart
63         rsync
64
65         movi    a4, 0x00040000
66         wsr     a4, ps
67         rsync
68
69         /* copy the loader to its address
70          * Note: The loader itself is a very small piece, so we assume we
71          *       don't partially overlap. We also assume (even more important)
72          *       that the kernel image is out of the way. Usually, when the
73          *       load address of this image is not at an arbitrary address,
74          *       but aligned to some 10K's we shouldn't overlap.
75          */
76
77         /* Note: The assembler cannot relax "addi a0, a0, ..." to an
78            l32r, so we load to a4 first. */
79
80         # addi  a4, a0, __start - __start_a0
81         # mov   a0, a4
82
83         movi    a4, __start
84         movi    a5, __start_a0
85         add     a4, a0, a4
86         sub     a0, a4, a5
87
88         movi    a4, __start
89         movi    a5, __reloc_end
90
91         # a0: address where this code has been loaded
92         # a4: compiled address of __start
93         # a5: compiled end address
94
95         mov.n   a7, a0
96         mov.n   a8, a4
97
98 1:
99         l32i    a10, a7, 0
100         l32i    a11, a7, 4
101         s32i    a10, a8, 0
102         s32i    a11, a8, 4
103         l32i    a10, a7, 8
104         l32i    a11, a7, 12
105         s32i    a10, a8, 8
106         s32i    a11, a8, 12
107         addi    a8, a8, 16
108         addi    a7, a7, 16
109         blt     a8, a5, 1b
110
111
112         /* We have to flush and invalidate the caches here before we jump. */
113
114 #if XCHAL_DCACHE_IS_WRITEBACK
115
116         ___flush_dcache_all a5 a6
117
118 #endif
119
120         ___invalidate_icache_all a5 a6
121         isync
122
123         movi    a11, _reloc
124         jx      a11
125
126         .globl _reloc
127 _reloc:
128
129         /* RedBoot is now at the end of the memory, so we don't have
130          * to copy the parameter list. Keep the code around; in case
131          * we need it again. */
132 #if 0
133         # a0: load address
134         # a2: start address of parameter list
135         # a3: length of parameter list
136         # a4: __start
137
138         /* copy the parameter list out of the way */
139
140         movi    a6, _param_start
141         add     a3, a2, a3
142 2:
143         l32i    a8, a2, 0
144         s32i    a8, a6, 0
145         addi    a2, a2, 4
146         addi    a6, a6, 4
147         blt     a2, a3, 2b
148 #endif
149
150         /* clear BSS section */
151         movi    a6, __bss_start
152         movi    a7, __bss_end
153         movi.n  a5, 0
154 3:
155         s32i    a5, a6, 0
156         addi    a6, a6, 4
157         blt     a6, a7, 3b
158
159         movi    a5, -16
160         movi    a1, _stack + STACK_SIZE
161         and     a1, a1, a5
162
163         /* Uncompress the kernel */
164
165         # a0: load address
166         # a2: boot parameter
167         # a4: __start
168
169         movi    a3, __image_load
170         sub     a4, a3, a4
171         add     a8, a0, a4
172
173         # a1  Stack
174         # a8(a4)  Load address of the image
175
176         movi    a6, _image_start
177         movi    a10, _image_end
178         movi    a7, 0x1000000
179         sub     a11, a10, a6
180         movi    a9, complen
181         s32i    a11, a9, 0
182
183         movi    a0, 0
184
185         # a6 destination
186         # a7 maximum size of destination
187         # a8 source
188         # a9 ptr to length
189
190         .extern gunzip
191         movi    a4, gunzip
192         beqz    a4, 1f
193
194         callx4  a4
195
196         j       2f
197
198
199         # a6 destination start
200         # a7 maximum size of destination
201         # a8 source start
202         # a9 ptr to length
203         # a10 destination end
204
205 1:
206         l32i    a9, a8, 0
207         l32i    a11, a8, 4
208         s32i    a9, a6, 0
209         s32i    a11, a6, 4
210         l32i    a9, a8, 8
211         l32i    a11, a8, 12
212         s32i    a9, a6, 8
213         s32i    a11, a6, 12
214         addi    a6, a6, 16
215         addi    a8, a8, 16
216         blt     a6, a10, 1b
217
218
219         /* jump to the kernel */
220 2:
221 #if XCHAL_DCACHE_IS_WRITEBACK
222
223         ___flush_dcache_all a5 a6
224
225 #endif
226
227         ___invalidate_icache_all a5 a6
228
229         isync
230
231         # a2  Boot parameter list
232
233         movi    a0, _image_start
234         jx      a0
235
236         .align 16
237         .data
238         .globl avail_ram
239 avail_ram:
240         .long   _heap
241         .globl end_avail
242 end_avail:
243         .long   _heap + HEAP_SIZE
244
245         .comm _stack, STACK_SIZE
246         .comm _heap, HEAP_SIZE
247
248         .globl end_avail
249         .comm complen, 4
250
251         .end    literal_prefix