watchdog: Make set_timeout function optional
authorGuenter Roeck <linux@roeck-us.net>
Sun, 28 Feb 2016 21:12:14 +0000 (13:12 -0800)
committerWim Van Sebroeck <wim@iguana.be>
Wed, 16 Mar 2016 20:11:07 +0000 (21:11 +0100)
For some watchdogs, the watchdog driver handles timeout changes without
explicitly setting any registers. In this situation, the watchdog driver
might only set the 'timeout' variable but do nothing else.
This can as well be handled by the infrastructure, so make the set_timeout
callback optional. If WDIOF_SETTIMEOUT is configured but the .set_timeout
callback is not available, update the timeout variable in the
infrastructure code.

Signed-off-by: Guenter Roeck <linux@roeck-us.net>
Signed-off-by: Wim Van Sebroeck <wim@iguana.be>
Documentation/watchdog/watchdog-kernel-api.txt
drivers/watchdog/watchdog_dev.c

index 55120a055a14d57f98053cb7147b25ad4c2a6214..dd8f912c05760e43dde2dc6df15dd413c0fa1ba2 100644 (file)
@@ -156,6 +156,11 @@ they are supported. These optional routines/operations are:
   because the watchdog does not necessarily has a 1 second resolution).
   (Note: the WDIOF_SETTIMEOUT needs to be set in the options field of the
   watchdog's info structure).
+  If the watchdog driver does not have to perform any action but setting the
+  watchdog_device.timeout, this callback can be omitted.
+  If set_timeout is not provided but, WDIOF_SETTIMEOUT is set, the watchdog
+  infrastructure updates the timeout value of the watchdog_device internally
+  to the requested value.
 * get_timeleft: this routines returns the time that's left before a reset.
 * restart: this routine restarts the machine. It returns 0 on success or a
   negative errno code for failure.
index ba2ecce4aae685df4ce30a8263fec56f3e0b729d..b5e700186ae00bbe3838a0bc71efd7d4e093db57 100644 (file)
@@ -183,13 +183,20 @@ static unsigned int watchdog_get_status(struct watchdog_device *wdd)
 static int watchdog_set_timeout(struct watchdog_device *wdd,
                                                        unsigned int timeout)
 {
-       if (!wdd->ops->set_timeout || !(wdd->info->options & WDIOF_SETTIMEOUT))
+       int err = 0;
+
+       if (!(wdd->info->options & WDIOF_SETTIMEOUT))
                return -EOPNOTSUPP;
 
        if (watchdog_timeout_invalid(wdd, timeout))
                return -EINVAL;
 
-       return wdd->ops->set_timeout(wdd, timeout);
+       if (wdd->ops->set_timeout)
+               err = wdd->ops->set_timeout(wdd, timeout);
+       else
+               wdd->timeout = timeout;
+
+       return err;
 }
 
 /*