~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

TOMOYO Linux Cross Reference
Linux/arch/loongarch/kernel/relocate_kernel.S

Version: ~ [ linux-6.12-rc7 ] ~ [ linux-6.11.7 ] ~ [ linux-6.10.14 ] ~ [ linux-6.9.12 ] ~ [ linux-6.8.12 ] ~ [ linux-6.7.12 ] ~ [ linux-6.6.60 ] ~ [ linux-6.5.13 ] ~ [ linux-6.4.16 ] ~ [ linux-6.3.13 ] ~ [ linux-6.2.16 ] ~ [ linux-6.1.116 ] ~ [ linux-6.0.19 ] ~ [ linux-5.19.17 ] ~ [ linux-5.18.19 ] ~ [ linux-5.17.15 ] ~ [ linux-5.16.20 ] ~ [ linux-5.15.171 ] ~ [ linux-5.14.21 ] ~ [ linux-5.13.19 ] ~ [ linux-5.12.19 ] ~ [ linux-5.11.22 ] ~ [ linux-5.10.229 ] ~ [ linux-5.9.16 ] ~ [ linux-5.8.18 ] ~ [ linux-5.7.19 ] ~ [ linux-5.6.19 ] ~ [ linux-5.5.19 ] ~ [ linux-5.4.285 ] ~ [ linux-5.3.18 ] ~ [ linux-5.2.21 ] ~ [ linux-5.1.21 ] ~ [ linux-5.0.21 ] ~ [ linux-4.20.17 ] ~ [ linux-4.19.323 ] ~ [ linux-4.18.20 ] ~ [ linux-4.17.19 ] ~ [ linux-4.16.18 ] ~ [ linux-4.15.18 ] ~ [ linux-4.14.336 ] ~ [ linux-4.13.16 ] ~ [ linux-4.12.14 ] ~ [ linux-4.11.12 ] ~ [ linux-4.10.17 ] ~ [ linux-4.9.337 ] ~ [ linux-4.4.302 ] ~ [ linux-3.10.108 ] ~ [ linux-2.6.32.71 ] ~ [ linux-2.6.0 ] ~ [ linux-2.4.37.11 ] ~ [ unix-v6-master ] ~ [ ccs-tools-1.8.12 ] ~ [ policy-sample ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

  1 /* SPDX-License-Identifier: GPL-2.0 */
  2 /*
  3  * relocate_kernel.S for kexec
  4  *
  5  * Copyright (C) 2022 Loongson Technology Corporation Limited
  6  */
  7 
  8 #include <linux/kexec.h>
  9 
 10 #include <asm/asm.h>
 11 #include <asm/asmmacro.h>
 12 #include <asm/regdef.h>
 13 #include <asm/loongarch.h>
 14 #include <asm/stackframe.h>
 15 #include <asm/addrspace.h>
 16 
 17 SYM_CODE_START(relocate_new_kernel)
 18         UNWIND_HINT_UNDEFINED
 19         /*
 20          * a0: EFI boot flag for the new kernel
 21          * a1: Command line pointer for the new kernel
 22          * a2: System table pointer for the new kernel
 23          * a3: Start address to jump to after relocation
 24          * a4: Pointer to the current indirection page entry
 25          */
 26         move            s0, a4
 27 
 28         /*
 29          * In case of a kdump/crash kernel, the indirection page is not
 30          * populated as the kernel is directly copied to a reserved location
 31          */
 32         beqz            s0, done
 33 
 34 process_entry:
 35         PTR_L           s1, s0, 0
 36         PTR_ADDI        s0, s0, SZREG
 37 
 38         /* destination page */
 39         andi            s2, s1, IND_DESTINATION
 40         beqz            s2, 1f
 41         li.w            t0, ~0x1
 42         and             s3, s1, t0      /* store destination addr in s3 */
 43         b               process_entry
 44 
 45 1:
 46         /* indirection page, update s0  */
 47         andi            s2, s1, IND_INDIRECTION
 48         beqz            s2, 1f
 49         li.w            t0, ~0x2
 50         and             s0, s1, t0
 51         b               process_entry
 52 
 53 1:
 54         /* done page */
 55         andi            s2, s1, IND_DONE
 56         beqz            s2, 1f
 57         b               done
 58 
 59 1:
 60         /* source page */
 61         andi            s2, s1, IND_SOURCE
 62         beqz            s2, process_entry
 63         li.w            t0, ~0x8
 64         and             s1, s1, t0
 65         li.w            s5, (1 << _PAGE_SHIFT) / SZREG
 66 
 67 copy_word:
 68         /* copy page word by word */
 69         REG_L           s4, s1, 0
 70         REG_S           s4, s3, 0
 71         PTR_ADDI        s3, s3, SZREG
 72         PTR_ADDI        s1, s1, SZREG
 73         LONG_ADDI       s5, s5, -1
 74         beqz            s5, process_entry
 75         b               copy_word
 76 
 77 done:
 78         ibar            0
 79         dbar            0
 80 
 81         /*
 82          * Jump to the new kernel,
 83          * make sure the values of a0, a1, a2 and a3 are not changed.
 84          */
 85         jr              a3
 86 SYM_CODE_END(relocate_new_kernel)
 87 
 88 #ifdef CONFIG_SMP
 89 /*
 90  * Other CPUs should wait until code is relocated and
 91  * then start at the entry point from LOONGARCH_IOCSR_MBUF0.
 92  */
 93 SYM_CODE_START(kexec_smp_wait)
 94         UNWIND_HINT_UNDEFINED
 95 1:      li.w            t0, 0x100                       /* wait for init loop */
 96 2:      addi.w          t0, t0, -1                      /* limit mailbox access */
 97         bnez            t0, 2b
 98         li.w            t1, LOONGARCH_IOCSR_MBUF0
 99         iocsrrd.w       s0, t1                          /* check PC as an indicator */
100         beqz            s0, 1b
101         iocsrrd.d       s0, t1                          /* get PC via mailbox */
102 
103         li.d            t0, CACHE_BASE
104         or              s0, s0, t0                      /* s0 = TO_CACHE(s0) */
105         jr              s0                              /* jump to initial PC */
106 SYM_CODE_END(kexec_smp_wait)
107 #endif
108 
109 relocate_new_kernel_end:
110 
111         .section ".data"
112 SYM_DATA(relocate_new_kernel_size, .long relocate_new_kernel_end - relocate_new_kernel)

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

kernel.org | git.kernel.org | LWN.net | Project Home | SVN repository | Mail admin

Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.

sflogo.php