GNU Linux-libre 4.19.264-gnu1
[releases.git] / arch / arm / kernel / relocate_kernel.S
1 /* SPDX-License-Identifier: GPL-2.0 */
2 /*
3  * relocate_kernel.S - put the kernel image in place to boot
4  */
5
6 #include <linux/linkage.h>
7 #include <asm/assembler.h>
8 #include <asm/asm-offsets.h>
9 #include <asm/kexec.h>
10
11         .align  3       /* not needed for this code, but keeps fncpy() happy */
12
13 ENTRY(relocate_new_kernel)
14
15         adr     r7, relocate_new_kernel_end
16         ldr     r0, [r7, #KEXEC_INDIR_PAGE]
17         ldr     r1, [r7, #KEXEC_START_ADDR]
18
19         /*
20          * If there is no indirection page (we are doing crashdumps)
21          * skip any relocation.
22          */
23         cmp     r0, #0
24         beq     2f
25
26 0:      /* top, read another word for the indirection page */
27         ldr     r3, [r0],#4
28
29         /* Is it a destination page. Put destination address to r4 */
30         tst     r3,#1,0
31         beq     1f
32         bic     r4,r3,#1
33         b       0b
34 1:
35         /* Is it an indirection page */
36         tst     r3,#2,0
37         beq     1f
38         bic     r0,r3,#2
39         b       0b
40 1:
41
42         /* are we done ? */
43         tst     r3,#4,0
44         beq     1f
45         b       2f
46
47 1:
48         /* is it source ? */
49         tst     r3,#8,0
50         beq     0b
51         bic r3,r3,#8
52         mov r6,#1024
53 9:
54         ldr r5,[r3],#4
55         str r5,[r4],#4
56         subs r6,r6,#1
57         bne 9b
58         b 0b
59
60 2:
61         /* Jump to relocated kernel */
62         mov     lr, r1
63         mov     r0, #0
64         ldr     r1, [r7, #KEXEC_MACH_TYPE]
65         ldr     r2, [r7, #KEXEC_R2]
66  ARM(   ret     lr      )
67  THUMB( bx      lr      )
68
69 ENDPROC(relocate_new_kernel)
70
71         .align  3
72 relocate_new_kernel_end:
73
74         .globl relocate_new_kernel_size
75 relocate_new_kernel_size:
76         .long relocate_new_kernel_end - relocate_new_kernel
77
78