arm64: entry: Free up another register on kpti's tramp_exit path
authorJames Morse <james.morse@arm.com>
Tue, 23 Nov 2021 18:41:43 +0000 (18:41 +0000)
committerJames Morse <james.morse@arm.com>
Tue, 15 Feb 2022 17:39:05 +0000 (17:39 +0000)
Kpti stashes x30 in far_el1 while it uses x30 for all its work.

Making the vectors a per-cpu data structure will require a second
register.

Allow tramp_exit two registers before it unmaps the kernel, by
leaving x30 on the stack, and stashing x29 in far_el1.

Reviewed-by: Russell King (Oracle) <rmk+kernel@armlinux.org.uk>
Reviewed-by: Catalin Marinas <catalin.marinas@arm.com>
Signed-off-by: James Morse <james.morse@arm.com>
arch/arm64/kernel/entry.S

index bdbdb92b5f77113447c5d05dc832751feee9677e..45e89135dc112c184fc1724d701f7fe167ad7c2f 100644 (file)
@@ -419,14 +419,16 @@ alternative_else_nop_endif
        ldp     x24, x25, [sp, #16 * 12]
        ldp     x26, x27, [sp, #16 * 13]
        ldp     x28, x29, [sp, #16 * 14]
-       ldr     lr, [sp, #S_LR]
-       add     sp, sp, #PT_REGS_SIZE           // restore sp
 
        .if     \el == 0
-alternative_insn eret, nop, ARM64_UNMAP_KERNEL_AT_EL0
+alternative_if_not ARM64_UNMAP_KERNEL_AT_EL0
+       ldr     lr, [sp, #S_LR]
+       add     sp, sp, #PT_REGS_SIZE           // restore sp
+       eret
+alternative_else_nop_endif
 #ifdef CONFIG_UNMAP_KERNEL_AT_EL0
        bne     4f
-       msr     far_el1, x30
+       msr     far_el1, x29
        tramp_alias     x30, tramp_exit_native
        br      x30
 4:
@@ -434,6 +436,9 @@ alternative_insn eret, nop, ARM64_UNMAP_KERNEL_AT_EL0
        br      x30
 #endif
        .else
+       ldr     lr, [sp, #S_LR]
+       add     sp, sp, #PT_REGS_SIZE           // restore sp
+
        /* Ensure any device/NC reads complete */
        alternative_insn nop, "dmb sy", ARM64_WORKAROUND_1508412
 
@@ -674,10 +679,12 @@ alternative_else_nop_endif
        .macro tramp_exit, regsize = 64
        adr     x30, tramp_vectors
        msr     vbar_el1, x30
-       tramp_unmap_kernel      x30
+       ldr     lr, [sp, #S_LR]
+       tramp_unmap_kernel      x29
        .if     \regsize == 64
-       mrs     x30, far_el1
+       mrs     x29, far_el1
        .endif
+       add     sp, sp, #PT_REGS_SIZE           // restore sp
        eret
        sb
        .endm