1 From 000de5417107623925a4cf0310579f744ff43c28 Mon Sep 17 00:00:00 2001
2 From: Ansuel Smith <ansuelsmth@gmail.com>
3 Date: Tue, 4 Feb 2020 20:56:48 +0100
4 Subject: watchdog: qcom-wdt: disable pretimeout on timer platform
6 Some platform like ipq806x doesn't support pretimeout and define
7 some interrupts used by qcom,msm-timer. Change the driver to check
8 and use pretimeout only on qcom,kpss-wdt as it's the only platform
9 that actually supports it.
11 Signed-off-by: Ansuel Smith <ansuelsmth@gmail.com>
12 Reviewed-by: Guenter Roeck <linux@roeck-us.net>
13 Link: https://lore.kernel.org/r/20200204195648.23350-1-ansuelsmth@gmail.com
14 [groeck: Conflict resolution]
15 Signed-off-by: Guenter Roeck <linux@roeck-us.net>
16 Signed-off-by: Wim Van Sebroeck <wim@linux-watchdog.org>
18 drivers/watchdog/qcom-wdt.c | 31 +++++++++++++++++++++++--------
19 1 file changed, 23 insertions(+), 8 deletions(-)
21 --- a/drivers/watchdog/qcom-wdt.c
22 +++ b/drivers/watchdog/qcom-wdt.c
23 @@ -39,6 +39,11 @@ static const u32 reg_offset_data_kpss[]
24 [WDT_BITE_TIME] = 0x14,
27 +struct qcom_wdt_match_data {
33 struct watchdog_device wdd;
35 @@ -168,19 +173,29 @@ static void qcom_clk_disable_unprepare(v
36 clk_disable_unprepare(data);
39 +static const struct qcom_wdt_match_data match_data_apcs_tmr = {
40 + .offset = reg_offset_data_apcs_tmr,
41 + .pretimeout = false,
44 +static const struct qcom_wdt_match_data match_data_kpss = {
45 + .offset = reg_offset_data_kpss,
49 static int qcom_wdt_probe(struct platform_device *pdev)
51 struct device *dev = &pdev->dev;
54 struct device_node *np = dev->of_node;
56 + const struct qcom_wdt_match_data *data;
61 - regs = of_device_get_match_data(dev);
63 + data = of_device_get_match_data(dev);
65 dev_err(dev, "Unsupported QCOM WDT module\n");
68 @@ -236,7 +251,7 @@ static int qcom_wdt_probe(struct platfor
70 /* check if there is pretimeout support */
71 irq = platform_get_irq_optional(pdev, 0);
73 + if (data->pretimeout && irq > 0) {
74 ret = devm_request_irq(dev, irq, qcom_wdt_isr,
76 "wdt_bark", &wdt->wdd);
77 @@ -256,7 +271,7 @@ static int qcom_wdt_probe(struct platfor
78 wdt->wdd.min_timeout = 1;
79 wdt->wdd.max_timeout = 0x10000000U / wdt->rate;
80 wdt->wdd.parent = dev;
82 + wdt->layout = data->offset;
84 if (readl(wdt_addr(wdt, WDT_STS)) & 1)
85 wdt->wdd.bootstatus = WDIOF_CARDRESET;
86 @@ -300,9 +315,9 @@ static int __maybe_unused qcom_wdt_resum
87 static SIMPLE_DEV_PM_OPS(qcom_wdt_pm_ops, qcom_wdt_suspend, qcom_wdt_resume);
89 static const struct of_device_id qcom_wdt_of_table[] = {
90 - { .compatible = "qcom,kpss-timer", .data = reg_offset_data_apcs_tmr },
91 - { .compatible = "qcom,scss-timer", .data = reg_offset_data_apcs_tmr },
92 - { .compatible = "qcom,kpss-wdt", .data = reg_offset_data_kpss },
93 + { .compatible = "qcom,kpss-timer", .data = &match_data_apcs_tmr },
94 + { .compatible = "qcom,scss-timer", .data = &match_data_apcs_tmr },
95 + { .compatible = "qcom,kpss-wdt", .data = &match_data_kpss },
98 MODULE_DEVICE_TABLE(of, qcom_wdt_of_table);