From d79b14d569544a0b0ed8e9d0d59e95061ab35f9b Mon Sep 17 00:00:00 2001 From: Linus Walleij Date: Tue, 13 Dec 2011 12:47:31 +0100 Subject: [PATCH] --- yaml --- r: 279797 b: refs/heads/master c: 5def51b0f827931bb559e6195060d774894fc9f9 h: refs/heads/master i: 279795: 431f5904dbd1d36cfeb137f1b2270b6dba42714c v: v3 --- [refs] | 2 +- trunk/arch/arm/kernel/smp_twd.c | 40 ++++++++++++++++++++++++++++++++- 2 files changed, 40 insertions(+), 2 deletions(-) diff --git a/[refs] b/[refs] index 32eea01c59a4..eee902588ce6 100644 --- a/[refs] +++ b/[refs] @@ -1,2 +1,2 @@ --- -refs/heads/master: 54d15b1d7ac550ecd8ab6b04309c2def614f8c80 +refs/heads/master: 5def51b0f827931bb559e6195060d774894fc9f9 diff --git a/trunk/arch/arm/kernel/smp_twd.c b/trunk/arch/arm/kernel/smp_twd.c index f0575610b17e..a9783947c086 100644 --- a/trunk/arch/arm/kernel/smp_twd.c +++ b/trunk/arch/arm/kernel/smp_twd.c @@ -10,8 +10,10 @@ */ #include #include +#include #include #include +#include #include #include #include @@ -25,6 +27,7 @@ /* set up by the platform code */ void __iomem *twd_base; +static struct clk *twd_clk; static unsigned long twd_timer_rate; static struct clock_event_device __percpu **twd_evt; @@ -140,6 +143,35 @@ static irqreturn_t twd_handler(int irq, void *dev_id) return IRQ_NONE; } +static struct clk *twd_get_clock(void) +{ + struct clk *clk; + int err; + + clk = clk_get_sys("smp_twd", NULL); + if (IS_ERR(clk)) { + pr_err("smp_twd: clock not found: %d\n", (int)PTR_ERR(clk)); + return clk; + } + + err = clk_prepare(clk); + if (err) { + pr_err("smp_twd: clock failed to prepare: %d\n", err); + clk_put(clk); + return ERR_PTR(err); + } + + err = clk_enable(clk); + if (err) { + pr_err("smp_twd: clock failed to enable: %d\n", err); + clk_unprepare(clk); + clk_put(clk); + return ERR_PTR(err); + } + + return clk; +} + /* * Setup the local clock events for a CPU. */ @@ -165,7 +197,13 @@ void __cpuinit twd_timer_setup(struct clock_event_device *clk) } } - twd_calibrate_rate(); + if (!twd_clk) + twd_clk = twd_get_clock(); + + if (!IS_ERR_OR_NULL(twd_clk)) + twd_timer_rate = clk_get_rate(twd_clk); + else + twd_calibrate_rate(); clk->name = "local_timer"; clk->features = CLOCK_EVT_FEAT_PERIODIC | CLOCK_EVT_FEAT_ONESHOT |