aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--arch/powerpc/platforms/ps3/setup.c12
-rw-r--r--drivers/ps3/ps3-sys-manager.c30
-rw-r--r--drivers/ps3/sys-manager-core.c16
-rw-r--r--include/asm-powerpc/ps3.h5
4 files changed, 44 insertions, 19 deletions
diff --git a/arch/powerpc/platforms/ps3/setup.c b/arch/powerpc/platforms/ps3/setup.c
index 5c2cbb08eb52..c144669a0d3f 100644
--- a/arch/powerpc/platforms/ps3/setup.c
+++ b/arch/powerpc/platforms/ps3/setup.c
@@ -95,6 +95,14 @@ static void ps3_power_off(void)
95 ps3_sys_manager_power_off(); /* never returns */ 95 ps3_sys_manager_power_off(); /* never returns */
96} 96}
97 97
98static void ps3_halt(void)
99{
100 DBG("%s:%d\n", __func__, __LINE__);
101
102 smp_send_stop();
103 ps3_sys_manager_halt(); /* never returns */
104}
105
98static void ps3_panic(char *str) 106static void ps3_panic(char *str)
99{ 107{
100 DBG("%s:%d %s\n", __func__, __LINE__, str); 108 DBG("%s:%d %s\n", __func__, __LINE__, str);
@@ -105,7 +113,8 @@ static void ps3_panic(char *str)
105 printk(" Please press POWER button.\n"); 113 printk(" Please press POWER button.\n");
106 printk("\n"); 114 printk("\n");
107 115
108 while(1); 116 while(1)
117 lv1_pause(1);
109} 118}
110 119
111#if defined(CONFIG_FB_PS3) || defined(CONFIG_FB_PS3_MODULE) || \ 120#if defined(CONFIG_FB_PS3) || defined(CONFIG_FB_PS3_MODULE) || \
@@ -266,6 +275,7 @@ define_machine(ps3) {
266 .progress = ps3_progress, 275 .progress = ps3_progress,
267 .restart = ps3_restart, 276 .restart = ps3_restart,
268 .power_off = ps3_power_off, 277 .power_off = ps3_power_off,
278 .halt = ps3_halt,
269#if defined(CONFIG_KEXEC) 279#if defined(CONFIG_KEXEC)
270 .kexec_cpu_down = ps3_kexec_cpu_down, 280 .kexec_cpu_down = ps3_kexec_cpu_down,
271 .machine_kexec = default_machine_kexec, 281 .machine_kexec = default_machine_kexec,
diff --git a/drivers/ps3/ps3-sys-manager.c b/drivers/ps3/ps3-sys-manager.c
index d4f6f960dd18..1260b01a5361 100644
--- a/drivers/ps3/ps3-sys-manager.c
+++ b/drivers/ps3/ps3-sys-manager.c
@@ -24,6 +24,7 @@
24#include <linux/reboot.h> 24#include <linux/reboot.h>
25 25
26#include <asm/firmware.h> 26#include <asm/firmware.h>
27#include <asm/lv1call.h>
27#include <asm/ps3.h> 28#include <asm/ps3.h>
28 29
29#include "vuart.h" 30#include "vuart.h"
@@ -581,6 +582,23 @@ fail_id:
581 return -EIO; 582 return -EIO;
582} 583}
583 584
585static void ps3_sys_manager_fin(struct ps3_system_bus_device *dev)
586{
587 ps3_sys_manager_send_request_shutdown(dev);
588
589 pr_emerg("System Halted, OK to turn off power\n");
590
591 while (ps3_sys_manager_handle_msg(dev)) {
592 /* pause until next DEC interrupt */
593 lv1_pause(0);
594 }
595
596 while (1) {
597 /* pause, ignoring DEC interrupt */
598 lv1_pause(1);
599 }
600}
601
584/** 602/**
585 * ps3_sys_manager_final_power_off - The final platform machine_power_off routine. 603 * ps3_sys_manager_final_power_off - The final platform machine_power_off routine.
586 * 604 *
@@ -602,12 +620,8 @@ static void ps3_sys_manager_final_power_off(struct ps3_system_bus_device *dev)
602 620
603 ps3_sys_manager_send_next_op(dev, PS3_SM_NEXT_OP_SYS_SHUTDOWN, 621 ps3_sys_manager_send_next_op(dev, PS3_SM_NEXT_OP_SYS_SHUTDOWN,
604 PS3_SM_WAKE_DEFAULT); 622 PS3_SM_WAKE_DEFAULT);
605 ps3_sys_manager_send_request_shutdown(dev);
606
607 pr_emerg("System Halted, OK to turn off power\n");
608 623
609 while (1) 624 ps3_sys_manager_fin(dev);
610 ps3_sys_manager_handle_msg(dev);
611} 625}
612 626
613/** 627/**
@@ -639,12 +653,8 @@ static void ps3_sys_manager_final_restart(struct ps3_system_bus_device *dev)
639 ps3_sys_manager_send_attr(dev, 0); 653 ps3_sys_manager_send_attr(dev, 0);
640 ps3_sys_manager_send_next_op(dev, PS3_SM_NEXT_OP_SYS_REBOOT, 654 ps3_sys_manager_send_next_op(dev, PS3_SM_NEXT_OP_SYS_REBOOT,
641 PS3_SM_WAKE_DEFAULT); 655 PS3_SM_WAKE_DEFAULT);
642 ps3_sys_manager_send_request_shutdown(dev);
643
644 pr_emerg("System Halted, OK to turn off power\n");
645 656
646 while (1) 657 ps3_sys_manager_fin(dev);
647 ps3_sys_manager_handle_msg(dev);
648} 658}
649 659
650/** 660/**
diff --git a/drivers/ps3/sys-manager-core.c b/drivers/ps3/sys-manager-core.c
index 31648f7d9ae1..474225852b63 100644
--- a/drivers/ps3/sys-manager-core.c
+++ b/drivers/ps3/sys-manager-core.c
@@ -19,6 +19,7 @@
19 */ 19 */
20 20
21#include <linux/kernel.h> 21#include <linux/kernel.h>
22#include <asm/lv1call.h>
22#include <asm/ps3.h> 23#include <asm/ps3.h>
23 24
24/** 25/**
@@ -50,10 +51,7 @@ void ps3_sys_manager_power_off(void)
50 if (ps3_sys_manager_ops.power_off) 51 if (ps3_sys_manager_ops.power_off)
51 ps3_sys_manager_ops.power_off(ps3_sys_manager_ops.dev); 52 ps3_sys_manager_ops.power_off(ps3_sys_manager_ops.dev);
52 53
53 printk(KERN_EMERG "System Halted, OK to turn off power\n"); 54 ps3_sys_manager_halt();
54 local_irq_disable();
55 while (1)
56 (void)0;
57} 55}
58 56
59void ps3_sys_manager_restart(void) 57void ps3_sys_manager_restart(void)
@@ -61,8 +59,14 @@ void ps3_sys_manager_restart(void)
61 if (ps3_sys_manager_ops.restart) 59 if (ps3_sys_manager_ops.restart)
62 ps3_sys_manager_ops.restart(ps3_sys_manager_ops.dev); 60 ps3_sys_manager_ops.restart(ps3_sys_manager_ops.dev);
63 61
64 printk(KERN_EMERG "System Halted, OK to turn off power\n"); 62 ps3_sys_manager_halt();
63}
64
65void ps3_sys_manager_halt(void)
66{
67 pr_emerg("System Halted, OK to turn off power\n");
65 local_irq_disable(); 68 local_irq_disable();
66 while (1) 69 while (1)
67 (void)0; 70 lv1_pause(1);
68} 71}
72
diff --git a/include/asm-powerpc/ps3.h b/include/asm-powerpc/ps3.h
index 2b693673eff4..d01c701bd27b 100644
--- a/include/asm-powerpc/ps3.h
+++ b/include/asm-powerpc/ps3.h
@@ -434,8 +434,9 @@ struct ps3_sys_manager_ops {
434}; 434};
435 435
436void ps3_sys_manager_register_ops(const struct ps3_sys_manager_ops *ops); 436void ps3_sys_manager_register_ops(const struct ps3_sys_manager_ops *ops);
437void ps3_sys_manager_power_off(void); 437void __noreturn ps3_sys_manager_power_off(void);
438void ps3_sys_manager_restart(void); 438void __noreturn ps3_sys_manager_restart(void);
439void __noreturn ps3_sys_manager_halt(void);
439 440
440struct ps3_prealloc { 441struct ps3_prealloc {
441 const char *name; 442 const char *name;