drivers/watchdog/sl28cpld_wdt.c

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

File Facts

System
Linux kernel
Corpus path
drivers/watchdog/sl28cpld_wdt.c
Extension
.c
Size
5622 bytes
Lines
228
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

struct sl28cpld_wdt {
	struct watchdog_device wdd;
	struct regmap *regmap;
	u32 offset;
	bool assert_wdt_timeout;
};

static int sl28cpld_wdt_ping(struct watchdog_device *wdd)
{
	struct sl28cpld_wdt *wdt = watchdog_get_drvdata(wdd);

	return regmap_write(wdt->regmap, wdt->offset + WDT_KICK,
			    WDT_KICK_VALUE);
}

static int sl28cpld_wdt_start(struct watchdog_device *wdd)
{
	struct sl28cpld_wdt *wdt = watchdog_get_drvdata(wdd);
	unsigned int val;

	val = WDT_CTRL_EN | WDT_CTRL_ASSERT_SYS_RESET;
	if (wdt->assert_wdt_timeout)
		val |= WDT_CTRL_ASSERT_WDT_TIMEOUT;
	if (nowayout)
		val |= WDT_CTRL_LOCK;

	return regmap_update_bits(wdt->regmap, wdt->offset + WDT_CTRL,
				  val, val);
}

static int sl28cpld_wdt_stop(struct watchdog_device *wdd)
{
	struct sl28cpld_wdt *wdt = watchdog_get_drvdata(wdd);

	return regmap_update_bits(wdt->regmap, wdt->offset + WDT_CTRL,
				  WDT_CTRL_EN, 0);
}

static unsigned int sl28cpld_wdt_get_timeleft(struct watchdog_device *wdd)
{
	struct sl28cpld_wdt *wdt = watchdog_get_drvdata(wdd);
	unsigned int val;
	int ret;

	ret = regmap_read(wdt->regmap, wdt->offset + WDT_COUNT, &val);
	if (ret)
		return 0;

	return val;
}

static int sl28cpld_wdt_set_timeout(struct watchdog_device *wdd,
				    unsigned int timeout)
{
	struct sl28cpld_wdt *wdt = watchdog_get_drvdata(wdd);
	int ret;

	ret = regmap_write(wdt->regmap, wdt->offset + WDT_TIMEOUT, timeout);
	if (ret)
		return ret;

	wdd->timeout = timeout;

	return 0;
}

static const struct watchdog_info sl28cpld_wdt_info = {
	.options = WDIOF_MAGICCLOSE | WDIOF_SETTIMEOUT | WDIOF_KEEPALIVEPING,
	.identity = "sl28cpld watchdog",
};

static const struct watchdog_ops sl28cpld_wdt_ops = {
	.owner = THIS_MODULE,
	.start = sl28cpld_wdt_start,
	.stop = sl28cpld_wdt_stop,
	.ping = sl28cpld_wdt_ping,
	.set_timeout = sl28cpld_wdt_set_timeout,
	.get_timeleft = sl28cpld_wdt_get_timeleft,
};

static int sl28cpld_wdt_probe(struct platform_device *pdev)
{
	struct watchdog_device *wdd;
	struct sl28cpld_wdt *wdt;
	unsigned int status;
	unsigned int val;
	int ret;

	if (!pdev->dev.parent)
		return -ENODEV;

Annotation

Implementation Notes