Commit 9d6b4efc16b3e8e7414fcd6aab8fec42756ba920

Authored by Shubhrajyoti Datta
Committed by Wim Van Sebroeck
1 parent d2a0015174

watchdog: xilinx: Add clock support

Add support for the clock. Currently we enable
at probe and relinquish at remove.

Reviewed-by: Guenter Roeck <linux@roeck-us.net>
Acked-by: Sören Brinkmann <soren.brinkmann@xilinx.com>
Signed-off-by: Shubhrajyoti Datta <shubhrajyoti.datta@xilinx.com>
Acked-by: Rob Herring <robh@kernel.org>
Signed-off-by: Guenter Roeck <linux@roeck-us.net>
Signed-off-by: Wim Van Sebroeck <wim@iguana.be>

Showing 2 changed files with 26 additions and 2 deletions Side-by-side Diff

Documentation/devicetree/bindings/watchdog/of-xilinx-wdt.txt
... ... @@ -7,6 +7,8 @@
7 7 - reg : Physical base address and size
8 8  
9 9 Optional properties:
  10 +- clocks : Input clock specifier. Refer to common clock
  11 + bindings.
10 12 - clock-frequency : Frequency of clock in Hz
11 13 - xlnx,wdt-enable-once : 0 - Watchdog can be restarted
12 14 1 - Watchdog can be enabled just once
... ... @@ -17,6 +19,7 @@
17 19 axi-timebase-wdt@40100000 {
18 20 clock-frequency = <50000000>;
19 21 compatible = "xlnx,xps-timebase-wdt-1.00.a";
  22 + clocks = <&clkc 15>;
20 23 reg = <0x40100000 0x10000>;
21 24 xlnx,wdt-enable-once = <0x0>;
22 25 xlnx,wdt-interval = <0x1b>;
drivers/watchdog/of_xilinx_wdt.c
... ... @@ -10,6 +10,7 @@
10 10 * 2 of the License, or (at your option) any later version.
11 11 */
12 12  
  13 +#include <linux/clk.h>
13 14 #include <linux/err.h>
14 15 #include <linux/module.h>
15 16 #include <linux/types.h>
... ... @@ -45,6 +46,7 @@
45 46 u32 wdt_interval;
46 47 spinlock_t spinlock;
47 48 struct watchdog_device xilinx_wdt_wdd;
  49 + struct clk *clk;
48 50 };
49 51  
50 52 static int xilinx_wdt_start(struct watchdog_device *wdd)
51 53  
52 54  
... ... @@ -195,16 +197,30 @@
195 197 spin_lock_init(&xdev->spinlock);
196 198 watchdog_set_drvdata(xilinx_wdt_wdd, xdev);
197 199  
  200 + xdev->clk = devm_clk_get(&pdev->dev, NULL);
  201 + if (IS_ERR(xdev->clk)) {
  202 + if (PTR_ERR(xdev->clk) == -ENOENT)
  203 + xdev->clk = NULL;
  204 + else
  205 + return PTR_ERR(xdev->clk);
  206 + }
  207 +
  208 + rc = clk_prepare_enable(xdev->clk);
  209 + if (rc) {
  210 + dev_err(&pdev->dev, "unable to enable clock\n");
  211 + return rc;
  212 + }
  213 +
198 214 rc = xwdt_selftest(xdev);
199 215 if (rc == XWT_TIMER_FAILED) {
200 216 dev_err(&pdev->dev, "SelfTest routine error\n");
201   - return rc;
  217 + goto err_clk_disable;
202 218 }
203 219  
204 220 rc = watchdog_register_device(xilinx_wdt_wdd);
205 221 if (rc) {
206 222 dev_err(&pdev->dev, "Cannot register watchdog (err=%d)\n", rc);
207   - return rc;
  223 + goto err_clk_disable;
208 224 }
209 225  
210 226 dev_info(&pdev->dev, "Xilinx Watchdog Timer at %p with timeout %ds\n",
... ... @@ -213,6 +229,10 @@
213 229 platform_set_drvdata(pdev, xdev);
214 230  
215 231 return 0;
  232 +err_clk_disable:
  233 + clk_disable_unprepare(xdev->clk);
  234 +
  235 + return rc;
216 236 }
217 237  
218 238 static int xwdt_remove(struct platform_device *pdev)
... ... @@ -220,6 +240,7 @@
220 240 struct xwdt_device *xdev = platform_get_drvdata(pdev);
221 241  
222 242 watchdog_unregister_device(&xdev->xilinx_wdt_wdd);
  243 + clk_disable_unprepare(xdev->clk);
223 244  
224 245 return 0;
225 246 }