diff options
author | Marek Szyprowski <m.szyprowski@samsung.com> | 2011-09-05 07:10:06 -0400 |
---|---|---|
committer | Kukjin Kim <kgene.kim@samsung.com> | 2011-09-15 00:59:58 -0400 |
commit | caf27307fa322f079338480c7a3387e79d7d3712 (patch) | |
tree | 44e8e7e19967906feff0d9173d7618eb1c58b5b8 | |
parent | 0685d5ec3e8a2462c29920c1f8187a6c640b6fc9 (diff) |
ARM: SAMSUNG: fix watchdog reset issue with clk_get()
clkdev framework uses global mutex to protect clock tree, so it is not
possible to call clk_get() in interrupt context. This patch fixes this
issue and makes system reset by watchdog call working again.
Signed-off-by: Marek Szyprowski <m.szyprowski@samsung.com>
Signed-off-by: Kyungmin Park <kyungmin.park@samsung.com>
Signed-off-by: Kukjin Kim <kgene.kim@samsung.com>
-rw-r--r-- | arch/arm/plat-samsung/clock.c | 11 | ||||
-rw-r--r-- | arch/arm/plat-samsung/include/plat/clock.h | 3 | ||||
-rw-r--r-- | arch/arm/plat-samsung/include/plat/watchdog-reset.h | 10 |
3 files changed, 17 insertions, 7 deletions
diff --git a/arch/arm/plat-samsung/clock.c b/arch/arm/plat-samsung/clock.c index 302c42670bd1..3b4451979d1b 100644 --- a/arch/arm/plat-samsung/clock.c +++ b/arch/arm/plat-samsung/clock.c | |||
@@ -64,6 +64,17 @@ static LIST_HEAD(clocks); | |||
64 | */ | 64 | */ |
65 | DEFINE_SPINLOCK(clocks_lock); | 65 | DEFINE_SPINLOCK(clocks_lock); |
66 | 66 | ||
67 | /* Global watchdog clock used by arch_wtd_reset() callback */ | ||
68 | struct clk *s3c2410_wdtclk; | ||
69 | static int __init s3c_wdt_reset_init(void) | ||
70 | { | ||
71 | s3c2410_wdtclk = clk_get(NULL, "watchdog"); | ||
72 | if (IS_ERR(s3c2410_wdtclk)) | ||
73 | printk(KERN_WARNING "%s: warning: cannot get watchdog clock\n", __func__); | ||
74 | return 0; | ||
75 | } | ||
76 | arch_initcall(s3c_wdt_reset_init); | ||
77 | |||
67 | /* enable and disable calls for use with the clk struct */ | 78 | /* enable and disable calls for use with the clk struct */ |
68 | 79 | ||
69 | static int clk_null_enable(struct clk *clk, int enable) | 80 | static int clk_null_enable(struct clk *clk, int enable) |
diff --git a/arch/arm/plat-samsung/include/plat/clock.h b/arch/arm/plat-samsung/include/plat/clock.h index 87d5b38a86fb..8f95700d296e 100644 --- a/arch/arm/plat-samsung/include/plat/clock.h +++ b/arch/arm/plat-samsung/include/plat/clock.h | |||
@@ -121,3 +121,6 @@ extern int s3c64xx_sclk_ctrl(struct clk *clk, int enable); | |||
121 | 121 | ||
122 | extern void s3c_pwmclk_init(void); | 122 | extern void s3c_pwmclk_init(void); |
123 | 123 | ||
124 | /* Global watchdog clock used by arch_wtd_reset() callback */ | ||
125 | |||
126 | extern struct clk *s3c2410_wdtclk; | ||
diff --git a/arch/arm/plat-samsung/include/plat/watchdog-reset.h b/arch/arm/plat-samsung/include/plat/watchdog-reset.h index 54b762acb5a0..40dbb2b0ae22 100644 --- a/arch/arm/plat-samsung/include/plat/watchdog-reset.h +++ b/arch/arm/plat-samsung/include/plat/watchdog-reset.h | |||
@@ -10,6 +10,7 @@ | |||
10 | * published by the Free Software Foundation. | 10 | * published by the Free Software Foundation. |
11 | */ | 11 | */ |
12 | 12 | ||
13 | #include <plat/clock.h> | ||
13 | #include <plat/regs-watchdog.h> | 14 | #include <plat/regs-watchdog.h> |
14 | #include <mach/map.h> | 15 | #include <mach/map.h> |
15 | 16 | ||
@@ -19,17 +20,12 @@ | |||
19 | 20 | ||
20 | static inline void arch_wdt_reset(void) | 21 | static inline void arch_wdt_reset(void) |
21 | { | 22 | { |
22 | struct clk *wdtclk; | ||
23 | |||
24 | printk("arch_reset: attempting watchdog reset\n"); | 23 | printk("arch_reset: attempting watchdog reset\n"); |
25 | 24 | ||
26 | __raw_writel(0, S3C2410_WTCON); /* disable watchdog, to be safe */ | 25 | __raw_writel(0, S3C2410_WTCON); /* disable watchdog, to be safe */ |
27 | 26 | ||
28 | wdtclk = clk_get(NULL, "watchdog"); | 27 | if (s3c2410_wdtclk) |
29 | if (!IS_ERR(wdtclk)) { | 28 | clk_enable(s3c2410_wdtclk); |
30 | clk_enable(wdtclk); | ||
31 | } else | ||
32 | printk(KERN_WARNING "%s: warning: cannot get watchdog clock\n", __func__); | ||
33 | 29 | ||
34 | /* put initial values into count and data */ | 30 | /* put initial values into count and data */ |
35 | __raw_writel(0x80, S3C2410_WTCNT); | 31 | __raw_writel(0x80, S3C2410_WTCNT); |