|
@@ -9,6 +9,7 @@
|
|
|
|
|
|
#include <asm/page.h>
|
|
#include <asm/page.h>
|
|
#include <asm/ptrace.h>
|
|
#include <asm/ptrace.h>
|
|
|
|
+#include <asm/thread_info.h>
|
|
#include <asm/asm-offsets.h>
|
|
#include <asm/asm-offsets.h>
|
|
|
|
|
|
/*
|
|
/*
|
|
@@ -41,6 +42,9 @@ swsusp_arch_suspend:
|
|
/* Get pointer to save area */
|
|
/* Get pointer to save area */
|
|
lghi %r1,0x1000
|
|
lghi %r1,0x1000
|
|
|
|
|
|
|
|
+ /* Save CPU address */
|
|
|
|
+ stap __LC_CPU_ADDRESS(%r1)
|
|
|
|
+
|
|
/* Store registers */
|
|
/* Store registers */
|
|
mvc 0x318(4,%r1),__SF_EMPTY(%r15) /* move prefix to lowcore */
|
|
mvc 0x318(4,%r1),__SF_EMPTY(%r15) /* move prefix to lowcore */
|
|
stfpc 0x31c(%r1) /* store fpu control */
|
|
stfpc 0x31c(%r1) /* store fpu control */
|
|
@@ -105,12 +109,7 @@ swsusp_arch_resume:
|
|
/* Make all free pages stable */
|
|
/* Make all free pages stable */
|
|
lghi %r2,1
|
|
lghi %r2,1
|
|
brasl %r14,arch_set_page_states
|
|
brasl %r14,arch_set_page_states
|
|
-#ifdef CONFIG_SMP
|
|
|
|
- /* Save boot cpu number */
|
|
|
|
- brasl %r14,smp_get_phys_cpu_id
|
|
|
|
- larl %r1,saved_cpu_id
|
|
|
|
- st %r2,0(%r1)
|
|
|
|
-#endif
|
|
|
|
|
|
+
|
|
/* Deactivate DAT */
|
|
/* Deactivate DAT */
|
|
stnsm __SF_EMPTY(%r15),0xfb
|
|
stnsm __SF_EMPTY(%r15),0xfb
|
|
|
|
|
|
@@ -139,12 +138,10 @@ swsusp_arch_resume:
|
|
|
|
|
|
/* Reset System */
|
|
/* Reset System */
|
|
larl %r1,restart_entry
|
|
larl %r1,restart_entry
|
|
- larl %r2,restart_psw
|
|
|
|
|
|
+ larl %r2,.Lrestart_diag308_psw
|
|
og %r1,0(%r2)
|
|
og %r1,0(%r2)
|
|
stg %r1,0(%r0)
|
|
stg %r1,0(%r0)
|
|
- larl %r1,saved_pgm_check_psw
|
|
|
|
- mvc 0(16,%r1),__LC_PGM_NEW_PSW(%r0)
|
|
|
|
- larl %r1,new_pgm_check_psw
|
|
|
|
|
|
+ larl %r1,.Lnew_pgm_check_psw
|
|
epsw %r2,%r3
|
|
epsw %r2,%r3
|
|
stm %r2,%r3,0(%r1)
|
|
stm %r2,%r3,0(%r1)
|
|
mvc __LC_PGM_NEW_PSW(16,%r0),0(%r1)
|
|
mvc __LC_PGM_NEW_PSW(16,%r0),0(%r1)
|
|
@@ -154,12 +151,54 @@ restart_entry:
|
|
lhi %r1,1
|
|
lhi %r1,1
|
|
sigp %r1,%r0,0x12
|
|
sigp %r1,%r0,0x12
|
|
sam64
|
|
sam64
|
|
- larl %r1,new_pgm_check_psw
|
|
|
|
|
|
+ larl %r1,.Lnew_pgm_check_psw
|
|
lpswe 0(%r1)
|
|
lpswe 0(%r1)
|
|
pgm_check_entry:
|
|
pgm_check_entry:
|
|
- larl %r1,saved_pgm_check_psw
|
|
|
|
- mvc __LC_PGM_NEW_PSW(16,%r0),0(%r1)
|
|
|
|
|
|
|
|
|
|
+ /* Switch to original suspend CPU */
|
|
|
|
+ larl %r1,.Lresume_cpu /* Resume CPU address: r2 */
|
|
|
|
+ stap 0(%r1)
|
|
|
|
+ llgh %r2,0(%r1)
|
|
|
|
+ lghi %r3,0x1000
|
|
|
|
+ llgh %r1,__LC_CPU_ADDRESS(%r3) /* Suspend CPU address: r1 */
|
|
|
|
+ cgr %r1,%r2
|
|
|
|
+ je restore_registers /* r1 = r2 -> nothing to do */
|
|
|
|
+ larl %r4,.Lrestart_suspend_psw /* Set new restart PSW */
|
|
|
|
+ mvc __LC_RESTART_PSW(16,%r0),0(%r4)
|
|
|
|
+3:
|
|
|
|
+ sigp %r9,%r1,__SIGP_INITIAL_CPU_RESET
|
|
|
|
+ brc 8,4f /* accepted */
|
|
|
|
+ brc 2,3b /* busy, try again */
|
|
|
|
+
|
|
|
|
+ /* Suspend CPU not available -> panic */
|
|
|
|
+ larl %r15,init_thread_union
|
|
|
|
+ ahi %r15,1<<(PAGE_SHIFT+THREAD_ORDER)
|
|
|
|
+ larl %r2,.Lpanic_string
|
|
|
|
+ larl %r3,_sclp_print_early
|
|
|
|
+ lghi %r1,0
|
|
|
|
+ sam31
|
|
|
|
+ sigp %r1,%r0,0x12
|
|
|
|
+ basr %r14,%r3
|
|
|
|
+ larl %r3,.Ldisabled_wait_31
|
|
|
|
+ lpsw 0(%r3)
|
|
|
|
+4:
|
|
|
|
+ /* Switch to suspend CPU */
|
|
|
|
+ sigp %r9,%r1,__SIGP_RESTART /* start suspend CPU */
|
|
|
|
+ brc 2,4b /* busy, try again */
|
|
|
|
+5:
|
|
|
|
+ sigp %r9,%r2,__SIGP_STOP /* stop resume (current) CPU */
|
|
|
|
+6: j 6b
|
|
|
|
+
|
|
|
|
+restart_suspend:
|
|
|
|
+ larl %r1,.Lresume_cpu
|
|
|
|
+ llgh %r2,0(%r1)
|
|
|
|
+7:
|
|
|
|
+ sigp %r9,%r2,__SIGP_SENSE /* Wait for resume CPU */
|
|
|
|
+ brc 2,7b /* busy, try again */
|
|
|
|
+ tmll %r9,0x40 /* Test if resume CPU is stopped */
|
|
|
|
+ jz 7b
|
|
|
|
+
|
|
|
|
+restore_registers:
|
|
/* Restore registers */
|
|
/* Restore registers */
|
|
lghi %r13,0x1000 /* %r1 = pointer to save arae */
|
|
lghi %r13,0x1000 /* %r1 = pointer to save arae */
|
|
|
|
|
|
@@ -193,13 +232,6 @@ pgm_check_entry:
|
|
/* Pointer to save area */
|
|
/* Pointer to save area */
|
|
lghi %r13,0x1000
|
|
lghi %r13,0x1000
|
|
|
|
|
|
-#ifdef CONFIG_SMP
|
|
|
|
- /* Switch CPUs */
|
|
|
|
- larl %r1,saved_cpu_id
|
|
|
|
- llgf %r2,0(%r1)
|
|
|
|
- llgf %r3,0x318(%r13)
|
|
|
|
- brasl %r14,smp_switch_boot_cpu_in_resume
|
|
|
|
-#endif
|
|
|
|
/* Restore prefix register */
|
|
/* Restore prefix register */
|
|
spx 0x318(%r13)
|
|
spx 0x318(%r13)
|
|
|
|
|
|
@@ -217,13 +249,16 @@ pgm_check_entry:
|
|
|
|
|
|
.section .data.nosave,"aw",@progbits
|
|
.section .data.nosave,"aw",@progbits
|
|
.align 8
|
|
.align 8
|
|
-restart_psw:
|
|
|
|
|
|
+.Ldisabled_wait_31:
|
|
|
|
+ .long 0x000a0000,0x00000000
|
|
|
|
+.Lpanic_string:
|
|
|
|
+ .asciz "Resume not possible because suspend CPU is no longer available"
|
|
|
|
+ .align 8
|
|
|
|
+.Lrestart_diag308_psw:
|
|
.long 0x00080000,0x80000000
|
|
.long 0x00080000,0x80000000
|
|
-new_pgm_check_psw:
|
|
|
|
|
|
+.Lrestart_suspend_psw:
|
|
|
|
+ .quad 0x0000000180000000,restart_suspend
|
|
|
|
+.Lnew_pgm_check_psw:
|
|
.quad 0,pgm_check_entry
|
|
.quad 0,pgm_check_entry
|
|
-saved_pgm_check_psw:
|
|
|
|
- .quad 0,0
|
|
|
|
-#ifdef CONFIG_SMP
|
|
|
|
-saved_cpu_id:
|
|
|
|
- .long 0
|
|
|
|
-#endif
|
|
|
|
|
|
+.Lresume_cpu:
|
|
|
|
+ .byte 0,0
|