arm64: move sp_el0 and tpidr_el1 into cpu_suspend_ctx
authorMark Rutland <mark.rutland@arm.com>
Thu, 3 Nov 2016 20:23:09 +0000 (20:23 +0000)
committerCatalin Marinas <catalin.marinas@arm.com>
Fri, 11 Nov 2016 18:25:44 +0000 (18:25 +0000)
When returning from idle, we rely on the fact that thread_info lives at
the end of the kernel stack, and restore this by masking the saved stack
pointer. Subsequent patches will sever the relationship between the
stack and thread_info, and to cater for this we must save/restore sp_el0
explicitly, storing it in cpu_suspend_ctx.

As cpu_suspend_ctx must be doubleword aligned, this leaves us with an
extra slot in cpu_suspend_ctx. We can use this to save/restore tpidr_el1
in the same way, which simplifies the code, avoiding pointer chasing on
the restore path (as we no longer need to load thread_info::cpu followed
by the relevant slot in __per_cpu_offset based on this).

This patch stashes both registers in cpu_suspend_ctx.

Signed-off-by: Mark Rutland <mark.rutland@arm.com>
Tested-by: Laura Abbott <labbott@redhat.com>
Cc: James Morse <james.morse@arm.com>
Cc: Lorenzo Pieralisi <lorenzo.pieralisi@arm.com>
Cc: Will Deacon <will.deacon@arm.com>
Signed-off-by: Catalin Marinas <catalin.marinas@arm.com>
arch/arm64/include/asm/suspend.h
arch/arm64/kernel/sleep.S
arch/arm64/kernel/suspend.c
arch/arm64/mm/proc.S

index b8a313fd7a093e7ee874c9e75f5eab9a4c338d91..de5600f40adfcb8185abb56461d4d9f3846a1d88 100644 (file)
@@ -1,7 +1,7 @@
 #ifndef __ASM_SUSPEND_H
 #define __ASM_SUSPEND_H
 
-#define NR_CTX_REGS 10
+#define NR_CTX_REGS 12
 #define NR_CALLEE_SAVED_REGS 12
 
 /*
index 1bec41b5fda3917b2ed7583663a239f25c6126bf..df67652e46f0de3fcfcfa18dbf5d69c7a97815a1 100644 (file)
@@ -125,9 +125,6 @@ ENTRY(_cpu_resume)
        /* load sp from context */
        ldr     x2, [x0, #CPU_CTX_SP]
        mov     sp, x2
-       /* save thread_info */
-       and     x2, x2, #~(THREAD_SIZE - 1)
-       msr     sp_el0, x2
        /*
         * cpu_do_resume expects x0 to contain context address pointer
         */
index bb0cd787a9d31dc4762d3a98257b3e11d8afe6f0..1e3be9064cfa0424ba6443d97f786917ed89782f 100644 (file)
@@ -46,12 +46,6 @@ void notrace __cpu_suspend_exit(void)
         */
        cpu_uninstall_idmap();
 
-       /*
-        * Restore per-cpu offset before any kernel
-        * subsystem relying on it has a chance to run.
-        */
-       set_my_cpu_offset(per_cpu_offset(cpu));
-
        /*
         * PSTATE was not saved over suspend/resume, re-enable any detected
         * features that might not have been set correctly.
index 352c73b6a59ea3817c9f2c79a867e704b7c1009e..6a853a867d9e004fe19ed70d83e71942aa926268 100644 (file)
@@ -70,11 +70,14 @@ ENTRY(cpu_do_suspend)
        mrs     x8, mdscr_el1
        mrs     x9, oslsr_el1
        mrs     x10, sctlr_el1
+       mrs     x11, tpidr_el1
+       mrs     x12, sp_el0
        stp     x2, x3, [x0]
        stp     x4, xzr, [x0, #16]
        stp     x5, x6, [x0, #32]
        stp     x7, x8, [x0, #48]
        stp     x9, x10, [x0, #64]
+       stp     x11, x12, [x0, #80]
        ret
 ENDPROC(cpu_do_suspend)
 
@@ -90,6 +93,7 @@ ENTRY(cpu_do_resume)
        ldp     x6, x8, [x0, #32]
        ldp     x9, x10, [x0, #48]
        ldp     x11, x12, [x0, #64]
+       ldp     x13, x14, [x0, #80]
        msr     tpidr_el0, x2
        msr     tpidrro_el0, x3
        msr     contextidr_el1, x4
@@ -112,6 +116,8 @@ ENTRY(cpu_do_resume)
        msr     mdscr_el1, x10
 
        msr     sctlr_el1, x12
+       msr     tpidr_el1, x13
+       msr     sp_el0, x14
        /*
         * Restore oslsr_el1 by writing oslar_el1
         */