linux-watchdog 5.1-rc1 tag
-----BEGIN PGP SIGNATURE----- Version: GnuPG v2.0.14 (GNU/Linux) iEYEABECAAYFAlyFIfgACgkQ+iyteGJfRsqt4gCgrgwSrDhwW+u7NjyY48KGAPgt xM8AoM31H9C2HrT2IJuKa3FjIawceUfw =wj0o -----END PGP SIGNATURE----- Merge tag 'linux-watchdog-5.1-rc1' of git://www.linux-watchdog.org/linux-watchdog Pull watchdog updates from Wim Van Sebroeck: - a new watchdog driver for the Mellanox systems - renesas-wdt: Document r8a77470 support - numerous 'Mark expected switch fall-throughs' - qcom: Add suspend/resume support - some small fixes and documentation updates * tag 'linux-watchdog-5.1-rc1' of git://www.linux-watchdog.org/linux-watchdog: watchdog: w83877f_wdt: Mark expected switch fall-through watchdog: sc520_wdt: Mark expected switch fall-through watchdog: sbc60xxwdt: Mark expected switch fall-through watchdog: smsc37b787_wdt: Mark expected switch fall-through watchdog: sc1200: Mark expected switch fall-through watchdog: pc87413: Mark expected switch fall-through Documentation/watchdog: Add documentation mlx-wdt driver watchdog: mlx-wdt: introduce a watchdog driver for Mellanox systems. platform_data/mlxreg: additions for Mellanox watchdog driver. watchdog: Update sysfs documentation. watchdog: dw: remove useless pr_fmt watchdog: pika_wdt: drop pointless static qualifier in pikawdt_init watchdog/hpwdt: Update Kconfig documentation dt-bindings: watchdog: renesas-wdt: Document r8a77470 support watchdog: qcom: Add suspend/resume support
This commit is contained in:
commit
a089e4fed5
|
@ -49,3 +49,26 @@ Contact: Wim Van Sebroeck <wim@iguana.be>
|
|||
Description:
|
||||
It is a read only file. It is read to know about current
|
||||
value of timeout programmed.
|
||||
|
||||
What: /sys/class/watchdog/watchdogn/pretimeout
|
||||
Date: December 2016
|
||||
Contact: Wim Van Sebroeck <wim@iguana.be>
|
||||
Description:
|
||||
It is a read only file. It specifies the time in seconds before
|
||||
timeout when the pretimeout interrupt is delivered. Pretimeout
|
||||
is an optional feature.
|
||||
|
||||
What: /sys/class/watchdog/watchdogn/pretimeout_avaialable_governors
|
||||
Date: February 2017
|
||||
Contact: Wim Van Sebroeck <wim@iguana.be>
|
||||
Description:
|
||||
It is a read only file. It shows the pretimeout governors
|
||||
available for this watchdog.
|
||||
|
||||
What: /sys/class/watchdog/watchdogn/pretimeout_governor
|
||||
Date: February 2017
|
||||
Contact: Wim Van Sebroeck <wim@iguana.be>
|
||||
Description:
|
||||
It is a read/write file. When read, the currently assigned
|
||||
pretimeout governor is returned. When written, it sets
|
||||
the pretimeout governor.
|
||||
|
|
|
@ -8,6 +8,7 @@ Required properties:
|
|||
- "renesas,r8a7743-wdt" (RZ/G1M)
|
||||
- "renesas,r8a7744-wdt" (RZ/G1N)
|
||||
- "renesas,r8a7745-wdt" (RZ/G1E)
|
||||
- "renesas,r8a77470-wdt" (RZ/G1C)
|
||||
- "renesas,r8a774a1-wdt" (RZ/G2M)
|
||||
- "renesas,r8a774c0-wdt" (RZ/G2E)
|
||||
- "renesas,r8a7790-wdt" (R-Car H2)
|
||||
|
|
|
@ -0,0 +1,52 @@
|
|||
Mellanox watchdog drivers
|
||||
for x86 based system switches
|
||||
|
||||
This driver provides watchdog functionality for various Mellanox
|
||||
Ethernet and Infiniband switch systems.
|
||||
|
||||
Mellanox watchdog device is implemented in a programmable logic device.
|
||||
|
||||
There are 2 types of HW watchdog implementations.
|
||||
|
||||
Type 1:
|
||||
Actual HW timeout can be defined as a power of 2 msec.
|
||||
e.g. timeout 20 sec will be rounded up to 32768 msec.
|
||||
The maximum timeout period is 32 sec (32768 msec.),
|
||||
Get time-left isn't supported
|
||||
|
||||
Type 2:
|
||||
Actual HW timeout is defined in sec. and it's the same as
|
||||
a user-defined timeout.
|
||||
Maximum timeout is 255 sec.
|
||||
Get time-left is supported.
|
||||
|
||||
Type 1 HW watchdog implementation exist in old systems and
|
||||
all new systems have type 2 HW watchdog.
|
||||
Two types of HW implementation have also different register map.
|
||||
|
||||
Mellanox system can have 2 watchdogs: main and auxiliary.
|
||||
Main and auxiliary watchdog devices can be enabled together
|
||||
on the same system.
|
||||
There are several actions that can be defined in the watchdog:
|
||||
system reset, start fans on full speed and increase register counter.
|
||||
The last 2 actions are performed without a system reset.
|
||||
Actions without reset are provided for auxiliary watchdog device,
|
||||
which is optional.
|
||||
Watchdog can be started during a probe, in this case it will be
|
||||
pinged by watchdog core before watchdog device will be opened by
|
||||
user space application.
|
||||
Watchdog can be initialised in nowayout way, i.e. oncse started
|
||||
it can't be stopped.
|
||||
|
||||
This mlx-wdt driver supports both HW watchdog implementations.
|
||||
|
||||
Watchdog driver is probed from the common mlx_platform driver.
|
||||
Mlx_platform driver provides an appropriate set of registers for
|
||||
Mellanox watchdog device, identity name (mlx-wdt-main or mlx-wdt-aux),
|
||||
initial timeout, performed action in expiration and configuration flags.
|
||||
watchdog configuration flags: nowayout and start_at_boot, hw watchdog
|
||||
version - type1 or type2.
|
||||
The driver checks during initialization if the previous system reset
|
||||
was done by the watchdog. If yes, it makes a notification about this event.
|
||||
|
||||
Access to HW registers is performed through a generic regmap interface.
|
|
@ -241,6 +241,22 @@ config RAVE_SP_WATCHDOG
|
|||
help
|
||||
Support for the watchdog on RAVE SP device.
|
||||
|
||||
config MLX_WDT
|
||||
tristate "Mellanox Watchdog"
|
||||
depends on MELLANOX_PLATFORM
|
||||
select WATCHDOG_CORE
|
||||
select REGMAP
|
||||
help
|
||||
This is the driver for the hardware watchdog on Mellanox systems.
|
||||
If you are going to use it, say Y here, otherwise N.
|
||||
This driver can be used together with the watchdog daemon.
|
||||
It can also watch your kernel to make sure it doesn't freeze,
|
||||
and if it does, it reboots your system after a certain amount of
|
||||
time.
|
||||
|
||||
To compile this driver as a module, choose M here: the
|
||||
module will be called mlx-wdt.
|
||||
|
||||
# ALPHA Architecture
|
||||
|
||||
# ARM Architecture
|
||||
|
@ -1157,7 +1173,7 @@ config HP_WATCHDOG
|
|||
select WATCHDOG_CORE
|
||||
depends on X86 && PCI
|
||||
help
|
||||
A software monitoring watchdog and NMI sourcing driver. This driver
|
||||
A software monitoring watchdog and NMI handling driver. This driver
|
||||
will detect lockups and provide a stack trace. This is a driver that
|
||||
will only load on an HP ProLiant system with a minimum of iLO2 support.
|
||||
To compile this driver as a module, choose M here: the module will be
|
||||
|
@ -1175,12 +1191,13 @@ config KEMPLD_WDT
|
|||
called kempld_wdt.
|
||||
|
||||
config HPWDT_NMI_DECODING
|
||||
bool "NMI decoding support for the HP ProLiant iLO2+ Hardware Watchdog Timer"
|
||||
bool "NMI support for the HP ProLiant iLO2+ Hardware Watchdog Timer"
|
||||
depends on HP_WATCHDOG
|
||||
default y
|
||||
help
|
||||
When an NMI occurs this feature will make the necessary BIOS calls to
|
||||
log the cause of the NMI.
|
||||
Enables the NMI handler for the watchdog pretimeout NMI and the iLO
|
||||
"Generate NMI to System" virtual button. When an NMI is claimed
|
||||
by the driver, panic is called.
|
||||
|
||||
config SC1200_WDT
|
||||
tristate "National Semiconductor PC87307/PC97307 (ala SC1200) Watchdog"
|
||||
|
|
|
@ -142,6 +142,7 @@ obj-$(CONFIG_INTEL_MID_WATCHDOG) += intel-mid_wdt.o
|
|||
obj-$(CONFIG_INTEL_MEI_WDT) += mei_wdt.o
|
||||
obj-$(CONFIG_NI903X_WDT) += ni903x_wdt.o
|
||||
obj-$(CONFIG_NIC7018_WDT) += nic7018_wdt.o
|
||||
obj-$(CONFIG_MLX_WDT) += mlx_wdt.o
|
||||
|
||||
# M68K Architecture
|
||||
obj-$(CONFIG_M54xx_WATCHDOG) += m54xx_wdt.o
|
||||
|
|
|
@ -16,8 +16,6 @@
|
|||
* heartbeat requests after the watchdog device has been closed.
|
||||
*/
|
||||
|
||||
#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
|
||||
|
||||
#include <linux/bitops.h>
|
||||
#include <linux/clk.h>
|
||||
#include <linux/delay.h>
|
||||
|
|
|
@ -0,0 +1,290 @@
|
|||
// SPDX-License-Identifier: GPL-2.0+
|
||||
/*
|
||||
* Mellanox watchdog driver
|
||||
*
|
||||
* Copyright (C) 2019 Mellanox Technologies
|
||||
* Copyright (C) 2019 Michael Shych <mshych@mellanox.com>
|
||||
*/
|
||||
|
||||
#include <linux/bitops.h>
|
||||
#include <linux/device.h>
|
||||
#include <linux/errno.h>
|
||||
#include <linux/log2.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/platform_data/mlxreg.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/regmap.h>
|
||||
#include <linux/spinlock.h>
|
||||
#include <linux/types.h>
|
||||
#include <linux/watchdog.h>
|
||||
|
||||
#define MLXREG_WDT_CLOCK_SCALE 1000
|
||||
#define MLXREG_WDT_MAX_TIMEOUT_TYPE1 32
|
||||
#define MLXREG_WDT_MAX_TIMEOUT_TYPE2 255
|
||||
#define MLXREG_WDT_MIN_TIMEOUT 1
|
||||
#define MLXREG_WDT_OPTIONS_BASE (WDIOF_KEEPALIVEPING | WDIOF_MAGICCLOSE | \
|
||||
WDIOF_SETTIMEOUT)
|
||||
|
||||
/**
|
||||
* struct mlxreg_wdt - wd private data:
|
||||
*
|
||||
* @wdd: watchdog device;
|
||||
* @device: basic device;
|
||||
* @pdata: data received from platform driver;
|
||||
* @regmap: register map of parent device;
|
||||
* @timeout: defined timeout in sec.;
|
||||
* @action_idx: index for direct access to action register;
|
||||
* @timeout_idx:index for direct access to TO register;
|
||||
* @tleft_idx: index for direct access to time left register;
|
||||
* @ping_idx: index for direct access to ping register;
|
||||
* @reset_idx: index for direct access to reset cause register;
|
||||
* @wd_type: watchdog HW type;
|
||||
*/
|
||||
struct mlxreg_wdt {
|
||||
struct watchdog_device wdd;
|
||||
struct mlxreg_core_platform_data *pdata;
|
||||
void *regmap;
|
||||
int action_idx;
|
||||
int timeout_idx;
|
||||
int tleft_idx;
|
||||
int ping_idx;
|
||||
int reset_idx;
|
||||
enum mlxreg_wdt_type wdt_type;
|
||||
};
|
||||
|
||||
static void mlxreg_wdt_check_card_reset(struct mlxreg_wdt *wdt)
|
||||
{
|
||||
struct mlxreg_core_data *reg_data;
|
||||
u32 regval;
|
||||
int rc;
|
||||
|
||||
if (wdt->reset_idx == -EINVAL)
|
||||
return;
|
||||
|
||||
if (!(wdt->wdd.info->options & WDIOF_CARDRESET))
|
||||
return;
|
||||
|
||||
reg_data = &wdt->pdata->data[wdt->reset_idx];
|
||||
rc = regmap_read(wdt->regmap, reg_data->reg, ®val);
|
||||
if (!rc) {
|
||||
if (regval & ~reg_data->mask) {
|
||||
wdt->wdd.bootstatus = WDIOF_CARDRESET;
|
||||
dev_info(wdt->wdd.parent,
|
||||
"watchdog previously reset the CPU\n");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static int mlxreg_wdt_start(struct watchdog_device *wdd)
|
||||
{
|
||||
struct mlxreg_wdt *wdt = watchdog_get_drvdata(wdd);
|
||||
struct mlxreg_core_data *reg_data = &wdt->pdata->data[wdt->action_idx];
|
||||
|
||||
return regmap_update_bits(wdt->regmap, reg_data->reg, ~reg_data->mask,
|
||||
BIT(reg_data->bit));
|
||||
}
|
||||
|
||||
static int mlxreg_wdt_stop(struct watchdog_device *wdd)
|
||||
{
|
||||
struct mlxreg_wdt *wdt = watchdog_get_drvdata(wdd);
|
||||
struct mlxreg_core_data *reg_data = &wdt->pdata->data[wdt->action_idx];
|
||||
|
||||
return regmap_update_bits(wdt->regmap, reg_data->reg, ~reg_data->mask,
|
||||
~BIT(reg_data->bit));
|
||||
}
|
||||
|
||||
static int mlxreg_wdt_ping(struct watchdog_device *wdd)
|
||||
{
|
||||
struct mlxreg_wdt *wdt = watchdog_get_drvdata(wdd);
|
||||
struct mlxreg_core_data *reg_data = &wdt->pdata->data[wdt->ping_idx];
|
||||
|
||||
return regmap_update_bits_base(wdt->regmap, reg_data->reg,
|
||||
~reg_data->mask, BIT(reg_data->bit),
|
||||
NULL, false, true);
|
||||
}
|
||||
|
||||
static int mlxreg_wdt_set_timeout(struct watchdog_device *wdd,
|
||||
unsigned int timeout)
|
||||
{
|
||||
struct mlxreg_wdt *wdt = watchdog_get_drvdata(wdd);
|
||||
struct mlxreg_core_data *reg_data = &wdt->pdata->data[wdt->timeout_idx];
|
||||
u32 regval, set_time, hw_timeout;
|
||||
int rc;
|
||||
|
||||
if (wdt->wdt_type == MLX_WDT_TYPE1) {
|
||||
rc = regmap_read(wdt->regmap, reg_data->reg, ®val);
|
||||
if (rc)
|
||||
return rc;
|
||||
|
||||
hw_timeout = order_base_2(timeout * MLXREG_WDT_CLOCK_SCALE);
|
||||
regval = (regval & reg_data->mask) | hw_timeout;
|
||||
/* Rowndown to actual closest number of sec. */
|
||||
set_time = BIT(hw_timeout) / MLXREG_WDT_CLOCK_SCALE;
|
||||
} else {
|
||||
set_time = timeout;
|
||||
regval = timeout;
|
||||
}
|
||||
|
||||
wdd->timeout = set_time;
|
||||
rc = regmap_write(wdt->regmap, reg_data->reg, regval);
|
||||
|
||||
if (!rc) {
|
||||
/*
|
||||
* Restart watchdog with new timeout period
|
||||
* if watchdog is already started.
|
||||
*/
|
||||
if (watchdog_active(wdd)) {
|
||||
rc = mlxreg_wdt_stop(wdd);
|
||||
if (!rc)
|
||||
rc = mlxreg_wdt_start(wdd);
|
||||
}
|
||||
}
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
static unsigned int mlxreg_wdt_get_timeleft(struct watchdog_device *wdd)
|
||||
{
|
||||
struct mlxreg_wdt *wdt = watchdog_get_drvdata(wdd);
|
||||
struct mlxreg_core_data *reg_data = &wdt->pdata->data[wdt->tleft_idx];
|
||||
u32 regval;
|
||||
int rc;
|
||||
|
||||
rc = regmap_read(wdt->regmap, reg_data->reg, ®val);
|
||||
/* Return 0 timeleft in case of failure register read. */
|
||||
return rc == 0 ? regval : 0;
|
||||
}
|
||||
|
||||
static const struct watchdog_ops mlxreg_wdt_ops_type1 = {
|
||||
.start = mlxreg_wdt_start,
|
||||
.stop = mlxreg_wdt_stop,
|
||||
.ping = mlxreg_wdt_ping,
|
||||
.set_timeout = mlxreg_wdt_set_timeout,
|
||||
.owner = THIS_MODULE,
|
||||
};
|
||||
|
||||
static const struct watchdog_ops mlxreg_wdt_ops_type2 = {
|
||||
.start = mlxreg_wdt_start,
|
||||
.stop = mlxreg_wdt_stop,
|
||||
.ping = mlxreg_wdt_ping,
|
||||
.set_timeout = mlxreg_wdt_set_timeout,
|
||||
.get_timeleft = mlxreg_wdt_get_timeleft,
|
||||
.owner = THIS_MODULE,
|
||||
};
|
||||
|
||||
static const struct watchdog_info mlxreg_wdt_main_info = {
|
||||
.options = MLXREG_WDT_OPTIONS_BASE
|
||||
| WDIOF_CARDRESET,
|
||||
.identity = "mlx-wdt-main",
|
||||
};
|
||||
|
||||
static const struct watchdog_info mlxreg_wdt_aux_info = {
|
||||
.options = MLXREG_WDT_OPTIONS_BASE
|
||||
| WDIOF_ALARMONLY,
|
||||
.identity = "mlx-wdt-aux",
|
||||
};
|
||||
|
||||
static void mlxreg_wdt_config(struct mlxreg_wdt *wdt,
|
||||
struct mlxreg_core_platform_data *pdata)
|
||||
{
|
||||
struct mlxreg_core_data *data = pdata->data;
|
||||
int i;
|
||||
|
||||
wdt->reset_idx = -EINVAL;
|
||||
for (i = 0; i < pdata->counter; i++, data++) {
|
||||
if (strnstr(data->label, "action", sizeof(data->label)))
|
||||
wdt->action_idx = i;
|
||||
else if (strnstr(data->label, "timeout", sizeof(data->label)))
|
||||
wdt->timeout_idx = i;
|
||||
else if (strnstr(data->label, "timeleft", sizeof(data->label)))
|
||||
wdt->tleft_idx = i;
|
||||
else if (strnstr(data->label, "ping", sizeof(data->label)))
|
||||
wdt->ping_idx = i;
|
||||
else if (strnstr(data->label, "reset", sizeof(data->label)))
|
||||
wdt->reset_idx = i;
|
||||
}
|
||||
|
||||
wdt->pdata = pdata;
|
||||
if (strnstr(pdata->identity, mlxreg_wdt_main_info.identity,
|
||||
sizeof(mlxreg_wdt_main_info.identity)))
|
||||
wdt->wdd.info = &mlxreg_wdt_main_info;
|
||||
else
|
||||
wdt->wdd.info = &mlxreg_wdt_aux_info;
|
||||
|
||||
wdt->wdt_type = pdata->version;
|
||||
if (wdt->wdt_type == MLX_WDT_TYPE2) {
|
||||
wdt->wdd.ops = &mlxreg_wdt_ops_type2;
|
||||
wdt->wdd.max_timeout = MLXREG_WDT_MAX_TIMEOUT_TYPE2;
|
||||
} else {
|
||||
wdt->wdd.ops = &mlxreg_wdt_ops_type1;
|
||||
wdt->wdd.max_timeout = MLXREG_WDT_MAX_TIMEOUT_TYPE1;
|
||||
}
|
||||
wdt->wdd.min_timeout = MLXREG_WDT_MIN_TIMEOUT;
|
||||
}
|
||||
|
||||
static int mlxreg_wdt_init_timeout(struct mlxreg_wdt *wdt,
|
||||
struct mlxreg_core_platform_data *pdata)
|
||||
{
|
||||
u32 timeout;
|
||||
|
||||
timeout = pdata->data[wdt->timeout_idx].health_cntr;
|
||||
return mlxreg_wdt_set_timeout(&wdt->wdd, timeout);
|
||||
}
|
||||
|
||||
static int mlxreg_wdt_probe(struct platform_device *pdev)
|
||||
{
|
||||
struct mlxreg_core_platform_data *pdata;
|
||||
struct mlxreg_wdt *wdt;
|
||||
int rc;
|
||||
|
||||
pdata = dev_get_platdata(&pdev->dev);
|
||||
if (!pdata) {
|
||||
dev_err(&pdev->dev, "Failed to get platform data.\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
wdt = devm_kzalloc(&pdev->dev, sizeof(*wdt), GFP_KERNEL);
|
||||
if (!wdt)
|
||||
return -ENOMEM;
|
||||
|
||||
wdt->wdd.parent = &pdev->dev;
|
||||
wdt->regmap = pdata->regmap;
|
||||
mlxreg_wdt_config(wdt, pdata);
|
||||
|
||||
if ((pdata->features & MLXREG_CORE_WD_FEATURE_NOWAYOUT))
|
||||
watchdog_set_nowayout(&wdt->wdd, WATCHDOG_NOWAYOUT);
|
||||
watchdog_stop_on_reboot(&wdt->wdd);
|
||||
watchdog_stop_on_unregister(&wdt->wdd);
|
||||
watchdog_set_drvdata(&wdt->wdd, wdt);
|
||||
rc = mlxreg_wdt_init_timeout(wdt, pdata);
|
||||
if (rc)
|
||||
goto register_error;
|
||||
|
||||
if ((pdata->features & MLXREG_CORE_WD_FEATURE_START_AT_BOOT)) {
|
||||
rc = mlxreg_wdt_start(&wdt->wdd);
|
||||
if (rc)
|
||||
goto register_error;
|
||||
set_bit(WDOG_HW_RUNNING, &wdt->wdd.status);
|
||||
}
|
||||
mlxreg_wdt_check_card_reset(wdt);
|
||||
rc = devm_watchdog_register_device(&pdev->dev, &wdt->wdd);
|
||||
|
||||
register_error:
|
||||
if (rc)
|
||||
dev_err(&pdev->dev,
|
||||
"Cannot register watchdog device (err=%d)\n", rc);
|
||||
return rc;
|
||||
}
|
||||
|
||||
static struct platform_driver mlxreg_wdt_driver = {
|
||||
.probe = mlxreg_wdt_probe,
|
||||
.driver = {
|
||||
.name = "mlx-wdt",
|
||||
},
|
||||
};
|
||||
|
||||
module_platform_driver(mlxreg_wdt_driver);
|
||||
|
||||
MODULE_AUTHOR("Michael Shych <michaelsh@mellanox.com>");
|
||||
MODULE_DESCRIPTION("Mellanox watchdog driver");
|
||||
MODULE_LICENSE("GPL");
|
||||
MODULE_ALIAS("platform:mlx-wdt");
|
|
@ -437,7 +437,7 @@ static long pc87413_ioctl(struct file *file, unsigned int cmd,
|
|||
return -EINVAL;
|
||||
timeout = new_timeout;
|
||||
pc87413_refresh();
|
||||
/* fall through and return the new timeout... */
|
||||
/* fall through - and return the new timeout... */
|
||||
case WDIOC_GETTIMEOUT:
|
||||
new_timeout = timeout * 60;
|
||||
return put_user(new_timeout, uarg.i);
|
||||
|
|
|
@ -225,7 +225,7 @@ static int __init pikawdt_init(void)
|
|||
{
|
||||
struct device_node *np;
|
||||
void __iomem *fpga;
|
||||
static u32 post1;
|
||||
u32 post1;
|
||||
int ret;
|
||||
|
||||
np = of_find_compatible_node(NULL, NULL, "pika,fpga");
|
||||
|
|
|
@ -245,6 +245,28 @@ static int qcom_wdt_remove(struct platform_device *pdev)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int __maybe_unused qcom_wdt_suspend(struct device *dev)
|
||||
{
|
||||
struct qcom_wdt *wdt = dev_get_drvdata(dev);
|
||||
|
||||
if (watchdog_active(&wdt->wdd))
|
||||
qcom_wdt_stop(&wdt->wdd);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int __maybe_unused qcom_wdt_resume(struct device *dev)
|
||||
{
|
||||
struct qcom_wdt *wdt = dev_get_drvdata(dev);
|
||||
|
||||
if (watchdog_active(&wdt->wdd))
|
||||
qcom_wdt_start(&wdt->wdd);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static SIMPLE_DEV_PM_OPS(qcom_wdt_pm_ops, qcom_wdt_suspend, qcom_wdt_resume);
|
||||
|
||||
static const struct of_device_id qcom_wdt_of_table[] = {
|
||||
{ .compatible = "qcom,kpss-timer", .data = reg_offset_data_apcs_tmr },
|
||||
{ .compatible = "qcom,scss-timer", .data = reg_offset_data_apcs_tmr },
|
||||
|
@ -259,6 +281,7 @@ static struct platform_driver qcom_watchdog_driver = {
|
|||
.driver = {
|
||||
.name = KBUILD_MODNAME,
|
||||
.of_match_table = qcom_wdt_of_table,
|
||||
.pm = &qcom_wdt_pm_ops,
|
||||
},
|
||||
};
|
||||
module_platform_driver(qcom_watchdog_driver);
|
||||
|
|
|
@ -270,8 +270,8 @@ static long fop_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
|
|||
|
||||
timeout = new_timeout;
|
||||
wdt_keepalive();
|
||||
/* Fall through */
|
||||
}
|
||||
/* Fall through */
|
||||
case WDIOC_GETTIMEOUT:
|
||||
return put_user(timeout, p);
|
||||
default:
|
||||
|
|
|
@ -239,7 +239,7 @@ static long sc1200wdt_ioctl(struct file *file, unsigned int cmd,
|
|||
return -EINVAL;
|
||||
timeout = new_timeout;
|
||||
sc1200wdt_write_data(WDTO, timeout);
|
||||
/* fall through and return the new timeout */
|
||||
/* fall through - and return the new timeout */
|
||||
|
||||
case WDIOC_GETTIMEOUT:
|
||||
return put_user(timeout * 60, p);
|
||||
|
|
|
@ -324,8 +324,8 @@ static long fop_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
|
|||
return -EINVAL;
|
||||
|
||||
wdt_keepalive();
|
||||
/* Fall through */
|
||||
}
|
||||
/* Fall through */
|
||||
case WDIOC_GETTIMEOUT:
|
||||
return put_user(timeout, p);
|
||||
default:
|
||||
|
|
|
@ -478,7 +478,7 @@ static long wb_smsc_wdt_ioctl(struct file *file,
|
|||
return -EINVAL;
|
||||
timeout = new_timeout;
|
||||
wb_smsc_wdt_set_timeout(timeout);
|
||||
/* fall through and return the new timeout... */
|
||||
/* fall through - and return the new timeout... */
|
||||
case WDIOC_GETTIMEOUT:
|
||||
new_timeout = timeout;
|
||||
if (unit == UNIT_MINUTE)
|
||||
|
|
|
@ -292,8 +292,8 @@ static long fop_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
|
|||
|
||||
timeout = new_timeout;
|
||||
wdt_keepalive();
|
||||
/* Fall through */
|
||||
}
|
||||
/* Fall through */
|
||||
case WDIOC_GETTIMEOUT:
|
||||
return put_user(timeout, p);
|
||||
default:
|
||||
|
|
|
@ -35,6 +35,19 @@
|
|||
#define __LINUX_PLATFORM_DATA_MLXREG_H
|
||||
|
||||
#define MLXREG_CORE_LABEL_MAX_SIZE 32
|
||||
#define MLXREG_CORE_WD_FEATURE_NOWAYOUT BIT(0)
|
||||
#define MLXREG_CORE_WD_FEATURE_START_AT_BOOT BIT(1)
|
||||
|
||||
/**
|
||||
* enum mlxreg_wdt_type - type of HW watchdog
|
||||
*
|
||||
* TYPE1 HW watchdog implementation exist in old systems.
|
||||
* All new systems have TYPE2 HW watchdog.
|
||||
*/
|
||||
enum mlxreg_wdt_type {
|
||||
MLX_WDT_TYPE1,
|
||||
MLX_WDT_TYPE2,
|
||||
};
|
||||
|
||||
/**
|
||||
* struct mlxreg_hotplug_device - I2C device data:
|
||||
|
@ -112,11 +125,17 @@ struct mlxreg_core_item {
|
|||
* @data: instance private data;
|
||||
* @regmap: register map of parent device;
|
||||
* @counter: number of instances;
|
||||
* @features: supported features of device;
|
||||
* @version: implementation version;
|
||||
* @identity: device identity name;
|
||||
*/
|
||||
struct mlxreg_core_platform_data {
|
||||
struct mlxreg_core_data *data;
|
||||
void *regmap;
|
||||
int counter;
|
||||
u32 features;
|
||||
u32 version;
|
||||
char identity[MLXREG_CORE_LABEL_MAX_SIZE];
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
Loading…
Reference in New Issue