[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Xen-devel] [PATCH 1/3] Set up an event channel to accept suspend requests.



# HG changeset patch
# User Brendan Cully <brendan@xxxxxxxxx>
# Date 1215120859 25200
# Node ID af2845b0a746f9be5d7d087951ef99c0ca4a1687
# Parent  88e01408ec0da0c406fde22a0003bd870144f180
Set up an event channel to accept suspend requests.
This is much faster than going through xenstore.

Signed-off-by: Brendan Cullly <brendan@xxxxxxxxx>

diff --git a/drivers/xen/core/machine_reboot.c 
b/drivers/xen/core/machine_reboot.c
--- a/drivers/xen/core/machine_reboot.c
+++ b/drivers/xen/core/machine_reboot.c
@@ -25,6 +25,8 @@
  */
 void (*pm_power_off)(void);
 EXPORT_SYMBOL(pm_power_off);
+
+int setup_suspend_evtchn(void);
 
 void machine_emergency_restart(void)
 {
@@ -241,6 +243,7 @@
        if (!suspend_cancelled) {
                xencons_resume();
                xenbus_resume();
+               setup_suspend_evtchn();
        } else {
                xenbus_suspend_cancel();
        }
diff --git a/drivers/xen/core/reboot.c b/drivers/xen/core/reboot.c
--- a/drivers/xen/core/reboot.c
+++ b/drivers/xen/core/reboot.c
@@ -7,6 +7,7 @@
 #include <linux/sysrq.h>
 #include <asm/hypervisor.h>
 #include <xen/xenbus.h>
+#include <xen/evtchn.h>
 #include <linux/kmod.h>
 #include <linux/slab.h>
 #include <linux/workqueue.h>
@@ -217,6 +218,36 @@
        .callback = sysrq_handler
 };
 
+static irqreturn_t suspend_int(int irq, void* dev_id, struct pt_regs *ptregs)
+{
+       shutting_down = SHUTDOWN_SUSPEND;
+       schedule_work(&shutdown_work);
+
+       return IRQ_HANDLED;
+}
+
+int setup_suspend_evtchn(void)
+{
+       static int irq = -1;
+       int port;
+       char portstr[5]; /* 1024 max */
+
+       if (irq > 0)
+               unbind_from_irqhandler(irq, NULL);
+
+       irq = bind_listening_port_to_irqhandler(0, suspend_int, 0, "suspend",
+                                               NULL);
+       if (irq <= 0) {
+               return -1;
+       }
+       port = irq_to_evtchn_port(irq);
+       printk(KERN_INFO "suspend: event channel %d\n", port);
+       sprintf(portstr, "%d", port);
+       xenbus_write(XBT_NIL, "device/suspend", "event-channel", portstr);
+
+       return 0;
+}
+
 static int setup_shutdown_watcher(void)
 {
        int err;
@@ -234,6 +265,13 @@
        err = register_xenbus_watch(&sysrq_watch);
        if (err) {
                printk(KERN_ERR "Failed to set sysrq watcher\n");
+               return err;
+       }
+
+       /* suspend event channel */
+       err = setup_suspend_evtchn();
+       if (err) {
+               printk(KERN_ERR "Failed to register suspend event channel\n");
                return err;
        }
 

_______________________________________________
Xen-devel mailing list
Xen-devel@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-devel


 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.