drivers/watchdog/ie6xx_wdt.c

Source file repositories/reference/linux-study-clean/drivers/watchdog/ie6xx_wdt.c

File Facts

System
Linux kernel
Corpus path
drivers/watchdog/ie6xx_wdt.c
Extension
.c
Size
7591 bytes
Lines
316
Domain
Driver Families
Bucket
drivers/watchdog
Inferred role
Driver Families: implementation source
Status
source 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.

Dependency Surface

Detected Declarations

Annotated Snippet

// SPDX-License-Identifier: GPL-2.0-only
/*
 *      Intel Atom E6xx Watchdog driver
 *
 *      Copyright (C) 2011 Alexander Stein
 *                <alexander.stein@systec-electronic.com>
 */

#include <linux/module.h>
#include <linux/moduleparam.h>
#include <linux/platform_device.h>
#include <linux/io.h>
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/watchdog.h>
#include <linux/seq_file.h>
#include <linux/debugfs.h>
#include <linux/uaccess.h>
#include <linux/spinlock.h>

#define DRIVER_NAME "ie6xx_wdt"

#define PV1	0x00
#define PV2	0x04

#define RR0	0x0c
#define RR1	0x0d
#define WDT_RELOAD	0x01
#define WDT_TOUT	0x02

#define WDTCR	0x10
#define WDT_PRE_SEL	0x04
#define WDT_RESET_SEL	0x08
#define WDT_RESET_EN	0x10
#define WDT_TOUT_EN	0x20

#define DCR	0x14

#define WDTLR	0x18
#define WDT_LOCK	0x01
#define WDT_ENABLE	0x02
#define WDT_TOUT_CNF	0x03

#define MIN_TIME	1
#define MAX_TIME	(10 * 60) /* 10 minutes */
#define DEFAULT_TIME	60

static unsigned int timeout = DEFAULT_TIME;
module_param(timeout, uint, 0);
MODULE_PARM_DESC(timeout,
		"Default Watchdog timer setting ("
		__MODULE_STRING(DEFAULT_TIME) "s)."
		"The range is from 1 to 600");

static bool nowayout = WATCHDOG_NOWAYOUT;
module_param(nowayout, bool, 0);
MODULE_PARM_DESC(nowayout,
	"Watchdog cannot be stopped once started (default="
		__MODULE_STRING(WATCHDOG_NOWAYOUT) ")");

static u8 resetmode = 0x10;
module_param(resetmode, byte, 0);
MODULE_PARM_DESC(resetmode,
	"Resetmode bits: 0x08 warm reset (cold reset otherwise), "
	"0x10 reset enable, 0x20 disable toggle GPIO[4] (default=0x10)");

static struct {
	unsigned short sch_wdtba;
	spinlock_t unlock_sequence;
#ifdef CONFIG_DEBUG_FS
	struct dentry *debugfs;
#endif
} ie6xx_wdt_data;

/*
 * This is needed to write to preload and reload registers
 * struct ie6xx_wdt_data.unlock_sequence must be used
 * to prevent sequence interrupts
 */
static void ie6xx_wdt_unlock_registers(void)
{
	outb(0x80, ie6xx_wdt_data.sch_wdtba + RR0);
	outb(0x86, ie6xx_wdt_data.sch_wdtba + RR0);
}

static int ie6xx_wdt_ping(struct watchdog_device *wdd)
{
	spin_lock(&ie6xx_wdt_data.unlock_sequence);
	ie6xx_wdt_unlock_registers();
	outb(WDT_RELOAD, ie6xx_wdt_data.sch_wdtba + RR1);

Annotation

Implementation Notes