linux/drivers/watchdog/renesas_wdt.c

// SPDX-License-Identifier: GPL-2.0
/*
 * Watchdog driver for Renesas WDT watchdog
 *
 * Copyright (C) 2015-17 Wolfram Sang, Sang Engineering <[email protected]>
 * Copyright (C) 2015-17 Renesas Electronics Corporation
 */
#include <linux/bitops.h>
#include <linux/clk.h>
#include <linux/delay.h>
#include <linux/io.h>
#include <linux/iopoll.h>
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/of.h>
#include <linux/platform_device.h>
#include <linux/pm_runtime.h>
#include <linux/smp.h>
#include <linux/sys_soc.h>
#include <linux/watchdog.h>

#define RWTCNT
#define RWTCSRA
#define RWTCSRA_WOVF
#define RWTCSRA_WRFLG
#define RWTCSRA_TME
#define RWTCSRB

#define RWDT_DEFAULT_TIMEOUT

/*
 * In probe, clk_rate is checked to be not more than 16 bit * biggest clock
 * divider (12 bits). d is only a factor to fully utilize the WDT counter and
 * will not exceed its 16 bits. Thus, no overflow, we stay below 32 bits.
 */
#define MUL_BY_CLKS_PER_SEC(p, d)

/* d is 16 bit, clk_divs 12 bit -> no 32 bit overflow */
#define DIV_BY_CLKS_PER_SEC(p, d)

static const unsigned int clk_divs[] =;

static bool nowayout = WATCHDOG_NOWAYOUT;
module_param(nowayout, bool, 0);
MODULE_PARM_DESC();

struct rwdt_priv {};

static void rwdt_write(struct rwdt_priv *priv, u32 val, unsigned int reg)
{}

static int rwdt_init_timeout(struct watchdog_device *wdev)
{}

static void rwdt_wait_cycles(struct rwdt_priv *priv, unsigned int cycles)
{}

static int rwdt_start(struct watchdog_device *wdev)
{}

static int rwdt_stop(struct watchdog_device *wdev)
{}

static unsigned int rwdt_get_timeleft(struct watchdog_device *wdev)
{}

/* needs to be atomic - no RPM, no usleep_range, no scheduling! */
static int rwdt_restart(struct watchdog_device *wdev, unsigned long action,
			void *data)
{}

static const struct watchdog_info rwdt_ident =;

static const struct watchdog_ops rwdt_ops =;

#if defined(CONFIG_ARCH_RCAR_GEN2) && defined(CONFIG_SMP)
/*
 * Watchdog-reset integration is broken on early revisions of R-Car Gen2 SoCs
 */
static const struct soc_device_attribute rwdt_quirks_match[] = {
	{
		.soc_id = "r8a7790",
		.revision = "ES1.*",
		.data = (void *)1,	/* needs single CPU */
	}, {
		.soc_id = "r8a7791",
		.revision = "ES1.*",
		.data = (void *)1,	/* needs single CPU */
	}, {
		.soc_id = "r8a7792",
		.data = (void *)0,	/* needs SMP disabled */
	},
	{ /* sentinel */ }
};

static bool rwdt_blacklisted(struct device *dev)
{
	const struct soc_device_attribute *attr;

	attr = soc_device_match(rwdt_quirks_match);
	if (attr && setup_max_cpus > (uintptr_t)attr->data) {
		dev_info(dev, "Watchdog blacklisted on %s %s\n", attr->soc_id,
			 attr->revision);
		return true;
	}

	return false;
}
#else /* !CONFIG_ARCH_RCAR_GEN2 || !CONFIG_SMP */
static inline bool rwdt_blacklisted(struct device *dev) {}
#endif /* !CONFIG_ARCH_RCAR_GEN2 || !CONFIG_SMP */

static int rwdt_probe(struct platform_device *pdev)
{}

static void rwdt_remove(struct platform_device *pdev)
{}

static int __maybe_unused rwdt_suspend(struct device *dev)
{}

static int __maybe_unused rwdt_resume(struct device *dev)
{}

static SIMPLE_DEV_PM_OPS(rwdt_pm_ops, rwdt_suspend, rwdt_resume);

static const struct of_device_id rwdt_ids[] =;
MODULE_DEVICE_TABLE(of, rwdt_ids);

static struct platform_driver rwdt_driver =;
module_platform_driver();

MODULE_DESCRIPTION();
MODULE_LICENSE();
MODULE_AUTHOR();