| 1 | /* SPDX-License-Identifier: GPL-2.0 */
|
| 2 | /*
|
| 3 | * Copyright (C) 2020-2022 Loongson Technology Corporation Limited
|
| 4 | */
|
| 5 | |
| 6 | |
| 7 |
|
| 8 | |
| 9 | |
| 10 | |
| 11 | |
| 12 | |
| 13 | |
| 14 | |
| 15 |
|
| 16 | |
| 17 |
|
| 18 | |
| 19 |
|
| 20 | __HEAD
|
| 21 |
|
| 22 | _head:
|
| 23 | .word IMAGE_DOS_SIGNATURE /* "MZ", MS-DOS header */
|
| 24 | .org 0x8
|
| 25 | .dword _kernel_entry /* Kernel entry point (physical address) */
|
| 26 | .dword _kernel_asize /* Kernel image effective size */
|
| 27 | .quad PHYS_LINK_KADDR /* Kernel image load offset from start of RAM */
|
| 28 | .org 0x38 /* 0x20 ~ 0x37 reserved */
|
| 29 | .long LINUX_PE_MAGIC
|
| 30 | .long pe_header - _head /* Offset to the PE header */
|
| 31 |
|
| 32 | pe_header:
|
| 33 | __EFI_PE_HEADER
|
| 34 |
|
| 35 | SYM_DATA(kernel_asize, .long _kernel_asize);
|
| 36 | SYM_DATA(kernel_fsize, .long _kernel_fsize);
|
| 37 |
|
| 38 | |
| 39 |
|
| 40 | __REF
|
| 41 |
|
| 42 | .align 12
|
| 43 |
|
| 44 | SYM_CODE_START(kernel_entry) |
| 45 | UNWIND_HINT_END_OF_STACK
|
| 46 |
|
| 47 | SETUP_TWINS
|
| 48 | SETUP_MODES t0
|
| 49 | JUMP_VIRT_ADDR t0, t1
|
| 50 | SETUP_DMWINS t0
|
| 51 |
|
| 52 | la.pcrel t0, __bss_start |
| 53 | LONG_S zero, t0, 0
|
| 54 | la.pcrel t1, __bss_stop - LONGSIZE
|
| 55 | 1:
|
| 56 | PTR_ADDI t0, t0, LONGSIZE
|
| 57 | LONG_S zero, t0, 0
|
| 58 | bne t0, t1, 1b
|
| 59 |
|
| 60 | la.pcrel t0, fw_arg0
|
| 61 | PTR_S a0, t0, 0 |
| 62 | la.pcrel t0, fw_arg1
|
| 63 | PTR_S a1, t0, 0
|
| 64 | la.pcrel t0, fw_arg2
|
| 65 | PTR_S a2, t0, 0
|
| 66 |
|
| 67 | |
| 68 | LONG_LI t0, 0
|
| 69 | LONG_LI t1, CSR_STFILL
|
| 70 | csrxchg t0, t1, LOONGARCH_CSR_IMPCTL1
|
| 71 | |
| 72 | /* KSave3 used for percpu base, initialized as 0 */
|
| 73 | csrwr zero, PERCPU_BASE_KS
|
| 74 | /* GPR21 used for percpu base (runtime), initialized as 0 */
|
| 75 | move u0, zero
|
| 76 |
|
| 77 | la.pcrel tp, init_task
|
| 78 | la.pcrel t0, init_stack
|
| 79 | PTR_LI t1, _THREAD_SIZE
|
| 80 | PTR_ADD t0, t0, t1
|
| 81 | PTR_ADDI sp, t0, -PT_SIZE
|
| 82 | set_saved_sp sp, t0, t1
|
| 83 |
|
| 84 | |
| 85 |
|
| 86 | bl relocate_kernel
|
| 87 |
|
| 88 | |
| 89 | /* Repoint the sp into the new kernel */
|
| 90 | LONG_LPTR t0, tp, TASK_STACK
|
| 91 | PTR_LI t1, _THREAD_SIZE
|
| 92 | PTR_ADD t0, t0, t1
|
| 93 | PTR_ADDI sp, t0, -PT_SIZE
|
| 94 | set_saved_sp sp, t0, t1
|
| 95 |
|
| 96 | /* Jump to the new kernel: new_pc = current_pc + random_offset */
|
| 97 | pcaddi t0, 0
|
| 98 | PTR_ADD t0, t0, a0
|
| 99 | jirl zero, t0, 0xc
|
| 100 | |
| 101 |
|
| 102 | |
| 103 |
|
| 104 | |
| 105 | bl kasan_early_init
|
| 106 | |
| 107 |
|
| 108 | bl start_kernel
|
| 109 | ASM_BUG()
|
| 110 |
|
| 111 | SYM_CODE_END(kernel_entry)
|
| 112 |
|
| 113 | |
| 114 |
|
| 115 | /*
|
| 116 | * SMP slave cpus entry point. Board specific code for bootstrap calls this
|
| 117 | * function after setting up the stack and tp registers.
|
| 118 | */
|
| 119 | SYM_CODE_START(smpboot_entry)
|
| 120 | UNWIND_HINT_END_OF_STACK
|
| 121 |
|
| 122 | SETUP_TWINS
|
| 123 | SETUP_MODES t0
|
| 124 | JUMP_VIRT_ADDR t0, t1
|
| 125 | SETUP_DMWINS t0
|
| 126 |
|
| 127 | |
| 128 | LONG_LI t0, 0
|
| 129 | LONG_LI t1, CSR_STFILL
|
| 130 | csrxchg t0, t1, LOONGARCH_CSR_IMPCTL1
|
| 131 | |
| 132 | la.pcrel t0, cpuboot_data
|
| 133 | ld.d tp, t0, CPU_BOOT_TASK
|
| 134 | ld.d sp, t0, CPU_BOOT_STACK
|
| 135 | ld.d u0, t0, CPU_BOOT_OFFSET
|
| 136 |
|
| 137 | bl start_secondary
|
| 138 | ASM_BUG()
|
| 139 |
|
| 140 | SYM_CODE_END(smpboot_entry)
|
| 141 |
|
| 142 | |