From: Martin Schwidefsky <schwidefsky@de.ibm.com>
To: linux-kernel@vger.kernel.org, linux-s390@vger.kernel.org,
linux-pm@lists.linux-foundation.org
Cc: Heiko Carstens <heiko.carstens@de.ibm.com>,
Christian Borntraeger <borntraeger@de.ibm.com>,
Martin Schwidefsky <schwidefsky@de.ibm.com>
Subject: [patch 21/38] pm: vmwatchdog power management callbacks.
Date: Thu, 04 Jun 2009 18:19:08 +0200 [thread overview]
Message-ID: <20090604161904.626534361@de.ibm.com> (raw)
In-Reply-To: 20090604161847.513682672@de.ibm.com
[-- Attachment #1: pm_vmwatchdog.patch --]
[-- Type: text/plain, Size: 5240 bytes --]
From: Christian Borntraeger <borntraeger@de.ibm.com>
This patch implements suspend/hibernation for the vmwatchdog driver. The
pm_notifier_callchain is used to get control on PM events. Since watchdog
operation and suspend cannot work together in a reliable fashion, the open
flag is also used to prevent suspend and open from happening at the same
time.
The watchdog can also be active with no open file descriptor. This patch
adds another flag which is only changed in vmwdt_keep_alive and
vmwdt_disable.
Signed-off-by: Christian Borntraeger <borntraeger@de.ibm.com>
Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
---
drivers/s390/char/vmwatchdog.c | 81 ++++++++++++++++++++++++++++++++++++++---
1 file changed, 76 insertions(+), 5 deletions(-)
Index: linux-2.6/drivers/s390/char/vmwatchdog.c
===================================================================
--- linux-2.6.orig/drivers/s390/char/vmwatchdog.c
+++ linux-2.6/drivers/s390/char/vmwatchdog.c
@@ -1,17 +1,23 @@
/*
* Watchdog implementation based on z/VM Watchdog Timer API
*
+ * Copyright IBM Corp. 2004,2009
+ *
* The user space watchdog daemon can use this driver as
* /dev/vmwatchdog to have z/VM execute the specified CP
* command when the timeout expires. The default command is
* "IPL", which which cause an immediate reboot.
*/
+#define KMSG_COMPONENT "vmwatchdog"
+#define pr_fmt(fmt) KMSG_COMPONENT ": " fmt
+
#include <linux/init.h>
#include <linux/fs.h>
#include <linux/kernel.h>
#include <linux/miscdevice.h>
#include <linux/module.h>
#include <linux/moduleparam.h>
+#include <linux/suspend.h>
#include <linux/watchdog.h>
#include <linux/smp_lock.h>
@@ -43,6 +49,9 @@ static unsigned int vmwdt_interval = 60;
static unsigned long vmwdt_is_open;
static int vmwdt_expect_close;
+#define VMWDT_OPEN 0 /* devnode is open or suspend in progress */
+#define VMWDT_RUNNING 1 /* The watchdog is armed */
+
enum vmwdt_func {
/* function codes */
wdt_init = 0,
@@ -92,6 +101,7 @@ static int vmwdt_keepalive(void)
EBC_TOUPPER(ebc_cmd, MAX_CMDLEN);
func = vmwdt_conceal ? (wdt_init | wdt_conceal) : wdt_init;
+ set_bit(VMWDT_RUNNING, &vmwdt_is_open);
ret = __diag288(func, vmwdt_interval, ebc_cmd, len);
WARN_ON(ret != 0);
kfree(ebc_cmd);
@@ -102,6 +112,7 @@ static int vmwdt_disable(void)
{
int ret = __diag288(wdt_cancel, 0, "", 0);
WARN_ON(ret != 0);
+ clear_bit(VMWDT_RUNNING, &vmwdt_is_open);
return ret;
}
@@ -123,13 +134,13 @@ static int vmwdt_open(struct inode *i, s
{
int ret;
lock_kernel();
- if (test_and_set_bit(0, &vmwdt_is_open)) {
+ if (test_and_set_bit(VMWDT_OPEN, &vmwdt_is_open)) {
unlock_kernel();
return -EBUSY;
}
ret = vmwdt_keepalive();
if (ret)
- clear_bit(0, &vmwdt_is_open);
+ clear_bit(VMWDT_OPEN, &vmwdt_is_open);
unlock_kernel();
return ret ? ret : nonseekable_open(i, f);
}
@@ -139,7 +150,7 @@ static int vmwdt_close(struct inode *i,
if (vmwdt_expect_close == 42)
vmwdt_disable();
vmwdt_expect_close = 0;
- clear_bit(0, &vmwdt_is_open);
+ clear_bit(VMWDT_OPEN, &vmwdt_is_open);
return 0;
}
@@ -223,6 +234,57 @@ static ssize_t vmwdt_write(struct file *
return count;
}
+static int vmwdt_resume(void)
+{
+ clear_bit(VMWDT_OPEN, &vmwdt_is_open);
+ return NOTIFY_DONE;
+}
+
+/*
+ * It makes no sense to go into suspend while the watchdog is running.
+ * Depending on the memory size, the watchdog might trigger, while we
+ * are still saving the memory.
+ * We reuse the open flag to ensure that suspend and watchdog open are
+ * exclusive operations
+ */
+static int vmwdt_suspend(void)
+{
+ if (test_and_set_bit(VMWDT_OPEN, &vmwdt_is_open)) {
+ pr_err("The watchdog is in use. "
+ "This prevents hibernation or suspend.\n");
+ return NOTIFY_BAD;
+ }
+ if (test_bit(VMWDT_RUNNING, &vmwdt_is_open)) {
+ clear_bit(VMWDT_OPEN, &vmwdt_is_open);
+ pr_err("The watchdog is running. "
+ "This prevents hibernation or suspend.\n");
+ return NOTIFY_BAD;
+ }
+ return NOTIFY_DONE;
+}
+
+/*
+ * This function is called for suspend and resume.
+ */
+static int vmwdt_power_event(struct notifier_block *this, unsigned long event,
+ void *ptr)
+{
+ switch (event) {
+ case PM_POST_HIBERNATION:
+ case PM_POST_SUSPEND:
+ return vmwdt_resume();
+ case PM_HIBERNATION_PREPARE:
+ case PM_SUSPEND_PREPARE:
+ return vmwdt_suspend();
+ default:
+ return NOTIFY_DONE;
+ }
+}
+
+static struct notifier_block vmwdt_power_notifier = {
+ .notifier_call = vmwdt_power_event,
+};
+
static const struct file_operations vmwdt_fops = {
.open = &vmwdt_open,
.release = &vmwdt_close,
@@ -244,12 +306,21 @@ static int __init vmwdt_init(void)
ret = vmwdt_probe();
if (ret)
return ret;
- return misc_register(&vmwdt_dev);
+ ret = register_pm_notifier(&vmwdt_power_notifier);
+ if (ret)
+ return ret;
+ ret = misc_register(&vmwdt_dev);
+ if (ret) {
+ unregister_pm_notifier(&vmwdt_power_notifier);
+ return ret;
+ }
+ return 0;
}
module_init(vmwdt_init);
static void __exit vmwdt_exit(void)
{
- WARN_ON(misc_deregister(&vmwdt_dev) != 0);
+ unregister_pm_notifier(&vmwdt_power_notifier);
+ misc_deregister(&vmwdt_dev);
}
module_exit(vmwdt_exit);
--
blue skies,
Martin.
"Reality continues to ruin my life." - Calvin.
next prev parent reply other threads:[~2009-06-04 16:28 UTC|newest]
Thread overview: 58+ messages / expand[flat|nested] mbox.gz Atom feed top
2009-06-04 16:18 [patch 00/38] power management / hibernate support for s390 Martin Schwidefsky
2009-06-04 16:18 ` [patch 01/38] pm: Move nvs routines into a seperate file Martin Schwidefsky
2009-06-08 6:35 ` Pavel Machek
2009-06-08 15:36 ` Cornelia Huck
2009-06-08 18:48 ` Rafael J. Wysocki
2009-06-09 8:40 ` [PATCH v2] " Cornelia Huck
2009-06-09 19:58 ` Pavel Machek
2009-06-09 23:09 ` Rafael J. Wysocki
2009-06-11 13:32 ` Heiko Carstens
2009-06-11 19:58 ` Rafael J. Wysocki
2009-06-11 21:11 ` Pavel Machek
2009-06-11 21:46 ` Rafael J. Wysocki
2009-06-11 22:05 ` Pavel Machek
2009-06-11 22:29 ` Rafael J. Wysocki
2009-06-11 23:22 ` Pavel Machek
2009-06-11 23:28 ` Pavel Machek
2009-06-04 16:18 ` [patch 02/38] dasd: forward internal errors to dasd_sleep_on caller Martin Schwidefsky
2009-06-04 16:18 ` [patch 03/38] iucv: provide second per-cpu IUCV command parameter block Martin Schwidefsky
2009-06-04 16:18 ` [patch 04/38] device irq power management Martin Schwidefsky
2009-06-04 16:18 ` [patch 05/38] s390: hibernation support for s390 Martin Schwidefsky
2009-06-08 6:44 ` Pavel Machek
2009-06-09 13:34 ` Hans-Joachim Picht
2009-06-09 19:59 ` Pavel Machek
2009-06-10 9:48 ` Hans-Joachim Picht
2009-06-12 6:37 ` Martin Schwidefsky
2009-06-04 16:18 ` [patch 06/38] pm: ccw bus power management callbacks Martin Schwidefsky
2009-06-04 16:18 ` [patch 07/38] pm: ccwgroup " Martin Schwidefsky
2009-06-04 16:18 ` [patch 08/38] pm: css " Martin Schwidefsky
2009-06-04 16:18 ` [patch 09/38] pm: io subchannel driver " Martin Schwidefsky
2009-06-04 16:18 ` [patch 10/38] pm: chsc " Martin Schwidefsky
2009-06-04 16:18 ` [patch 11/38] pm: dasd " Martin Schwidefsky
2009-06-04 16:18 ` [patch 12/38] pm: add kernel_page_present Martin Schwidefsky
2009-06-04 16:19 ` [patch 13/38] pm: xpram driver power management callbacks Martin Schwidefsky
2009-06-04 16:19 ` [patch 14/38] cio: force console function Martin Schwidefsky
2009-06-04 16:19 ` [patch 15/38] pm: con3215 power management callbacks Martin Schwidefsky
2009-06-04 16:19 ` [patch 16/38] pm: lcs driver " Martin Schwidefsky
2009-06-04 16:19 ` [patch 17/38] pm: qeth " Martin Schwidefsky
2009-06-04 16:19 ` [patch 18/38] pm: ctcm " Martin Schwidefsky
2009-06-04 16:19 ` [patch 19/38] pm: claw " Martin Schwidefsky
2009-06-04 16:19 ` [patch 20/38] pm: zfcp " Martin Schwidefsky
2009-06-04 16:19 ` Martin Schwidefsky [this message]
2009-06-04 16:19 ` [patch 22/38] pm: appldata " Martin Schwidefsky
2009-06-04 16:19 ` [patch 23/38] pm: vmur driver " Martin Schwidefsky
2009-06-04 16:19 ` [patch 24/38] pm: vmlogrdr " Martin Schwidefsky
2009-06-04 16:19 ` [patch 25/38] pm: tape " Martin Schwidefsky
2009-06-04 16:19 ` [patch 26/38] pm: power management support for SCLP drivers Martin Schwidefsky
2009-06-04 16:19 ` [patch 27/38] iucv: establish reboot notifier Martin Schwidefsky
2009-06-04 16:19 ` [patch 28/38] pm: iucv power management callbacks Martin Schwidefsky
2009-06-04 16:19 ` [patch 29/38] pm: netiucv " Martin Schwidefsky
2009-06-04 16:19 ` [patch 30/38] PM: af_iucv " Martin Schwidefsky
2009-06-04 16:19 ` [patch 31/38] pm: hvc_iucv " Martin Schwidefsky
2009-06-04 16:19 ` [patch 32/38] pm: smsgiucv " Martin Schwidefsky
2009-06-04 16:19 ` [patch 33/38] pm: con3270 " Martin Schwidefsky
2009-06-04 16:19 ` [patch 34/38] pm: memory hotplug " Martin Schwidefsky
2009-06-04 16:19 ` [patch 35/38] pm: monwriter " Martin Schwidefsky
2009-06-04 16:19 ` [patch 36/38] pm: monreader " Martin Schwidefsky
2009-06-04 16:19 ` [patch 37/38] pm: dcssblk " Martin Schwidefsky
2009-06-04 16:19 ` [patch 38/38] pm: ap bus " Martin Schwidefsky
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20090604161904.626534361@de.ibm.com \
--to=schwidefsky@de.ibm.com \
--cc=borntraeger@de.ibm.com \
--cc=heiko.carstens@de.ibm.com \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-pm@lists.linux-foundation.org \
--cc=linux-s390@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox