patch-2.4.20 linux-2.4.20/drivers/s390/char/hwc_rw.c
Next file: linux-2.4.20/drivers/s390/char/tuball.c
Previous file: linux-2.4.20/drivers/s390/char/hwc.h
Back to the patch index
Back to the overall index
- Lines: 127
- Date:
Thu Nov 28 15:53:14 2002
- Orig file:
linux-2.4.19/drivers/s390/char/hwc_rw.c
- Orig date:
Sun Sep 30 12:26:07 2001
diff -urN linux-2.4.19/drivers/s390/char/hwc_rw.c linux-2.4.20/drivers/s390/char/hwc_rw.c
@@ -35,6 +35,8 @@
#define MIN(a,b) (((a<b) ? a : b))
#endif
+extern void ctrl_alt_del (void);
+
#define HWC_RW_PRINT_HEADER "hwc low level driver: "
#define USE_VM_DETECTION
@@ -172,6 +174,7 @@
unsigned char read_nonprio:1;
unsigned char read_prio:1;
unsigned char read_statechange:1;
+ unsigned char sig_quiesce:1;
unsigned char flags;
@@ -222,6 +225,7 @@
0,
0,
0,
+ 0,
NULL,
NULL
@@ -231,6 +235,8 @@
static unsigned long cr0_save __attribute__ ((aligned (8)));
static unsigned char psw_mask __attribute__ ((aligned (8)));
+static ext_int_info_t ext_int_info_hwc;
+
#define DELAYED_WRITE 0
#define IMMEDIATE_WRITE 1
@@ -1527,6 +1533,19 @@
HWC_RW_PRINT_HEADER
"can not read state change notifications\n");
+ hwc_data.sig_quiesce
+ = ((mask & ET_SigQuiesce_Mask) == ET_SigQuiesce_Mask);
+ if (hwc_data.sig_quiesce)
+ internal_print (
+ DELAYED_WRITE,
+ HWC_RW_PRINT_HEADER
+ "can receive signal quiesce\n");
+ else
+ internal_print (
+ DELAYED_WRITE,
+ HWC_RW_PRINT_HEADER
+ "can not receive signal quiesce\n");
+
hwc_data.read_nonprio
= ((mask & ET_OpCmd_Mask) == ET_OpCmd_Mask);
if (hwc_data.read_nonprio)
@@ -1607,6 +1626,48 @@
return retval;
}
+#ifdef CONFIG_SMP
+extern unsigned long cpu_online_map;
+static volatile unsigned long cpu_quiesce_map;
+
+static void
+do_load_quiesce_psw (void)
+{
+ psw_t quiesce_psw;
+
+ clear_bit (smp_processor_id (), &cpu_quiesce_map);
+ if (smp_processor_id () == 0) {
+
+ while (cpu_quiesce_map != 0) ;
+
+ quiesce_psw.mask = _DW_PSW_MASK;
+ quiesce_psw.addr = 0xfff;
+ __load_psw (quiesce_psw);
+ }
+ signal_processor (smp_processor_id (), sigp_stop);
+}
+
+static void
+do_machine_quiesce (void)
+{
+ cpu_quiesce_map = cpu_online_map;
+ smp_call_function (do_load_quiesce_psw, NULL, 0, 0);
+ do_load_quiesce_psw ();
+}
+
+#else
+static void
+do_machine_quiesce (void)
+{
+ psw_t quiesce_psw;
+
+ quiesce_psw.mask = _DW_PSW_MASK;
+ queisce_psw.addr = 0xfff;
+ __load_psw (quiesce_psw);
+}
+
+#endif
+
static int
process_evbufs (void *start, void *end)
{
@@ -1642,6 +1703,13 @@
retval += eval_statechangebuf
((statechangebuf_t *) evbuf);
break;
+ case ET_SigQuiesce:
+
+ _machine_restart = do_machine_quiesce;
+ _machine_halt = do_machine_quiesce;
+ _machine_power_off = do_machine_quiesce;
+ ctrl_alt_del ();
+ break;
default:
internal_print (
DELAYED_WRITE,
@@ -2004,7 +2072,8 @@
#endif
- if (register_external_interrupt (0x2401, hwc_interrupt_handler) != 0)
+ if (register_early_external_interrupt (0x2401, hwc_interrupt_handler,
+ &ext_int_info_hwc) != 0)
panic ("Couldn't request external interrupts 0x2401");
spin_lock_init (&hwc_data.lock);
FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen (who was at: slshen@lbl.gov)