in smsc37b787_wdt.c [419:486]
static long wb_smsc_wdt_ioctl(struct file *file,
unsigned int cmd, unsigned long arg)
{
int new_timeout;
union {
struct watchdog_info __user *ident;
int __user *i;
} uarg;
static const struct watchdog_info ident = {
.options = WDIOF_KEEPALIVEPING |
WDIOF_SETTIMEOUT |
WDIOF_MAGICCLOSE,
.firmware_version = 0,
.identity = "SMsC 37B787 Watchdog",
};
uarg.i = (int __user *)arg;
switch (cmd) {
case WDIOC_GETSUPPORT:
return copy_to_user(uarg.ident, &ident, sizeof(ident))
? -EFAULT : 0;
case WDIOC_GETSTATUS:
return put_user(wb_smsc_wdt_status(), uarg.i);
case WDIOC_GETBOOTSTATUS:
return put_user(0, uarg.i);
case WDIOC_SETOPTIONS:
{
int options, retval = -EINVAL;
if (get_user(options, uarg.i))
return -EFAULT;
if (options & WDIOS_DISABLECARD) {
wb_smsc_wdt_disable();
retval = 0;
}
if (options & WDIOS_ENABLECARD) {
wb_smsc_wdt_enable();
retval = 0;
}
return retval;
}
case WDIOC_KEEPALIVE:
wb_smsc_wdt_reset_timer();
return 0;
case WDIOC_SETTIMEOUT:
if (get_user(new_timeout, uarg.i))
return -EFAULT;
/* the API states this is given in secs */
if (unit == UNIT_MINUTE)
new_timeout /= 60;
if (new_timeout < 0 || new_timeout > MAX_TIMEOUT)
return -EINVAL;
timeout = new_timeout;
wb_smsc_wdt_set_timeout(timeout);
fallthrough; /* and return the new timeout */
case WDIOC_GETTIMEOUT:
new_timeout = timeout;
if (unit == UNIT_MINUTE)
new_timeout *= 60;
return put_user(new_timeout, uarg.i);
default:
return -ENOTTY;
}
}