drivers/watchdog/watchdog_core.c
Source file repositories/reference/linux-study-clean/drivers/watchdog/watchdog_core.c
File Facts
- System
- Linux kernel
- Corpus path
drivers/watchdog/watchdog_core.c- Extension
.c- Size
- 13615 bytes
- Lines
- 499
- Domain
- Driver Families
- Bucket
- drivers/watchdog
- Inferred role
- Driver Families: exported/initcall integration point
- Status
- integration implementation candidate
Why This File Exists
Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Exports symbols or registers init work; inspect boot/module ordering and who consumes the exported contract.
- Uses kernel synchronization; read lock ordering, sleepability, and interrupt context assumptions before translating.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/module.hlinux/types.hlinux/errno.hlinux/kernel.hlinux/reboot.hlinux/watchdog.hlinux/init.hlinux/idr.hlinux/err.hlinux/of.hlinux/property.hlinux/suspend.hwatchdog_core.htrace/events/watchdog.h
Detected Declarations
function watchdog_deferred_registration_addfunction watchdog_deferred_registration_delfunction list_for_each_safefunction watchdog_check_min_max_timeoutfunction watchdog_init_timeoutfunction watchdog_reboot_notifierfunction watchdog_restart_notifierfunction watchdog_pm_notifierfunction watchdog_set_restart_priorityfunction ___watchdog_register_devicefunction __watchdog_register_devicefunction watchdog_register_devicefunction __watchdog_unregister_devicefunction watchdog_unregister_devicefunction devm_watchdog_unregister_devicefunction devm_watchdog_register_devicefunction watchdog_deferred_registrationfunction watchdog_initfunction watchdog_exitexport watchdog_init_timeoutexport watchdog_set_restart_priorityexport watchdog_register_deviceexport watchdog_unregister_deviceexport devm_watchdog_register_device
Annotated Snippet
if (wdd_tmp == wdd) {
list_del(&wdd_tmp->deferred);
break;
}
}
}
static void watchdog_check_min_max_timeout(struct watchdog_device *wdd)
{
/*
* Check that we have valid min and max timeout values, if
* not reset them both to 0 (=not used or unknown)
*/
if (!wdd->max_hw_heartbeat_ms && wdd->min_timeout > wdd->max_timeout) {
pr_info("Invalid min and max timeout values, resetting to 0!\n");
wdd->min_timeout = 0;
wdd->max_timeout = 0;
}
}
/**
* watchdog_init_timeout() - initialize the timeout field
* @wdd: watchdog device
* @timeout_parm: timeout module parameter
* @dev: Device that stores the timeout-sec property
*
* Initialize the timeout field of the watchdog_device struct with either the
* timeout module parameter (if it is valid value) or the timeout-sec property
* (only if it is a valid value and the timeout_parm is out of bounds).
* If none of them are valid then we keep the old value (which should normally
* be the default timeout value). Note that for the module parameter, '0' means
* 'use default' while it is an invalid value for the timeout-sec property.
* It should simply be dropped if you want to use the default value then.
*
* A zero is returned on success or -EINVAL if all provided values are out of
* bounds.
*/
int watchdog_init_timeout(struct watchdog_device *wdd,
unsigned int timeout_parm,
const struct device *dev)
{
const char *dev_str = wdd->parent ? dev_name(wdd->parent) :
(const char *)wdd->info->identity;
unsigned int t = 0;
int ret = 0;
watchdog_check_min_max_timeout(wdd);
/* check the driver supplied value (likely a module parameter) first */
if (timeout_parm) {
if (!watchdog_timeout_invalid(wdd, timeout_parm)) {
wdd->timeout = timeout_parm;
return 0;
}
pr_err("%s: driver supplied timeout (%u) out of range\n",
dev_str, timeout_parm);
ret = -EINVAL;
}
/* try to get the timeout_sec property */
if (dev && device_property_read_u32(dev, "timeout-sec", &t) == 0) {
if (t && !watchdog_timeout_invalid(wdd, t)) {
wdd->timeout = t;
return 0;
}
pr_err("%s: DT supplied timeout (%u) out of range\n", dev_str, t);
ret = -EINVAL;
}
if (ret < 0 && wdd->timeout)
pr_warn("%s: falling back to default timeout (%u)\n", dev_str,
wdd->timeout);
return ret;
}
EXPORT_SYMBOL_GPL(watchdog_init_timeout);
static int watchdog_reboot_notifier(struct notifier_block *nb,
unsigned long code, void *data)
{
struct watchdog_device *wdd;
wdd = container_of(nb, struct watchdog_device, reboot_nb);
if (code == SYS_DOWN || code == SYS_HALT || code == SYS_POWER_OFF) {
if (watchdog_hw_running(wdd)) {
int ret;
ret = wdd->ops->stop(wdd);
trace_watchdog_stop(wdd, ret);
if (ret)
Annotation
- Immediate include surface: `linux/module.h`, `linux/types.h`, `linux/errno.h`, `linux/kernel.h`, `linux/reboot.h`, `linux/watchdog.h`, `linux/init.h`, `linux/idr.h`.
- Detected declarations: `function watchdog_deferred_registration_add`, `function watchdog_deferred_registration_del`, `function list_for_each_safe`, `function watchdog_check_min_max_timeout`, `function watchdog_init_timeout`, `function watchdog_reboot_notifier`, `function watchdog_restart_notifier`, `function watchdog_pm_notifier`, `function watchdog_set_restart_priority`, `function ___watchdog_register_device`.
- Atlas domain: Driver Families / drivers/watchdog.
- Implementation status: integration implementation candidate.
- Synchronization appears in or near this file; preserve lock ordering, sleepability, and interrupt-context constraints.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.