diff options
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/clocksource/time-armada-370-xp.c | 30 | ||||
-rw-r--r-- | drivers/clocksource/timer-marco.c | 23 | ||||
-rw-r--r-- | drivers/watchdog/orion_wdt.c | 42 |
3 files changed, 80 insertions, 15 deletions
diff --git a/drivers/clocksource/time-armada-370-xp.c b/drivers/clocksource/time-armada-370-xp.c index 0451e62fac7a..3a0704b0d739 100644 --- a/drivers/clocksource/time-armada-370-xp.c +++ b/drivers/clocksource/time-armada-370-xp.c | |||
@@ -293,6 +293,7 @@ static void __init armada_xp_timer_init(struct device_node *np) | |||
293 | 293 | ||
294 | /* The 25Mhz fixed clock is mandatory, and must always be available */ | 294 | /* The 25Mhz fixed clock is mandatory, and must always be available */ |
295 | BUG_ON(IS_ERR(clk)); | 295 | BUG_ON(IS_ERR(clk)); |
296 | clk_prepare_enable(clk); | ||
296 | timer_clk = clk_get_rate(clk); | 297 | timer_clk = clk_get_rate(clk); |
297 | 298 | ||
298 | armada_370_xp_timer_common_init(np); | 299 | armada_370_xp_timer_common_init(np); |
@@ -300,11 +301,40 @@ static void __init armada_xp_timer_init(struct device_node *np) | |||
300 | CLOCKSOURCE_OF_DECLARE(armada_xp, "marvell,armada-xp-timer", | 301 | CLOCKSOURCE_OF_DECLARE(armada_xp, "marvell,armada-xp-timer", |
301 | armada_xp_timer_init); | 302 | armada_xp_timer_init); |
302 | 303 | ||
304 | static void __init armada_375_timer_init(struct device_node *np) | ||
305 | { | ||
306 | struct clk *clk; | ||
307 | |||
308 | clk = of_clk_get_by_name(np, "fixed"); | ||
309 | if (!IS_ERR(clk)) { | ||
310 | clk_prepare_enable(clk); | ||
311 | timer_clk = clk_get_rate(clk); | ||
312 | } else { | ||
313 | |||
314 | /* | ||
315 | * This fallback is required in order to retain proper | ||
316 | * devicetree backwards compatibility. | ||
317 | */ | ||
318 | clk = of_clk_get(np, 0); | ||
319 | |||
320 | /* Must have at least a clock */ | ||
321 | BUG_ON(IS_ERR(clk)); | ||
322 | clk_prepare_enable(clk); | ||
323 | timer_clk = clk_get_rate(clk) / TIMER_DIVIDER; | ||
324 | timer25Mhz = false; | ||
325 | } | ||
326 | |||
327 | armada_370_xp_timer_common_init(np); | ||
328 | } | ||
329 | CLOCKSOURCE_OF_DECLARE(armada_375, "marvell,armada-375-timer", | ||
330 | armada_375_timer_init); | ||
331 | |||
303 | static void __init armada_370_timer_init(struct device_node *np) | 332 | static void __init armada_370_timer_init(struct device_node *np) |
304 | { | 333 | { |
305 | struct clk *clk = of_clk_get(np, 0); | 334 | struct clk *clk = of_clk_get(np, 0); |
306 | 335 | ||
307 | BUG_ON(IS_ERR(clk)); | 336 | BUG_ON(IS_ERR(clk)); |
337 | clk_prepare_enable(clk); | ||
308 | timer_clk = clk_get_rate(clk) / TIMER_DIVIDER; | 338 | timer_clk = clk_get_rate(clk) / TIMER_DIVIDER; |
309 | timer25Mhz = false; | 339 | timer25Mhz = false; |
310 | 340 | ||
diff --git a/drivers/clocksource/timer-marco.c b/drivers/clocksource/timer-marco.c index caf7a2030461..361a789d4bee 100644 --- a/drivers/clocksource/timer-marco.c +++ b/drivers/clocksource/timer-marco.c | |||
@@ -20,8 +20,6 @@ | |||
20 | #include <linux/of_address.h> | 20 | #include <linux/of_address.h> |
21 | #include <linux/sched_clock.h> | 21 | #include <linux/sched_clock.h> |
22 | 22 | ||
23 | #define MARCO_CLOCK_FREQ 1000000 | ||
24 | |||
25 | #define SIRFSOC_TIMER_32COUNTER_0_CTRL 0x0000 | 23 | #define SIRFSOC_TIMER_32COUNTER_0_CTRL 0x0000 |
26 | #define SIRFSOC_TIMER_32COUNTER_1_CTRL 0x0004 | 24 | #define SIRFSOC_TIMER_32COUNTER_1_CTRL 0x0004 |
27 | #define SIRFSOC_TIMER_MATCH_0 0x0018 | 25 | #define SIRFSOC_TIMER_MATCH_0 0x0018 |
@@ -40,6 +38,8 @@ | |||
40 | 38 | ||
41 | #define SIRFSOC_TIMER_REG_CNT 6 | 39 | #define SIRFSOC_TIMER_REG_CNT 6 |
42 | 40 | ||
41 | static unsigned long marco_timer_rate; | ||
42 | |||
43 | static const u32 sirfsoc_timer_reg_list[SIRFSOC_TIMER_REG_CNT] = { | 43 | static const u32 sirfsoc_timer_reg_list[SIRFSOC_TIMER_REG_CNT] = { |
44 | SIRFSOC_TIMER_WATCHDOG_EN, | 44 | SIRFSOC_TIMER_WATCHDOG_EN, |
45 | SIRFSOC_TIMER_32COUNTER_0_CTRL, | 45 | SIRFSOC_TIMER_32COUNTER_0_CTRL, |
@@ -195,7 +195,7 @@ static int sirfsoc_local_timer_setup(struct clock_event_device *ce) | |||
195 | ce->rating = 200; | 195 | ce->rating = 200; |
196 | ce->set_mode = sirfsoc_timer_set_mode; | 196 | ce->set_mode = sirfsoc_timer_set_mode; |
197 | ce->set_next_event = sirfsoc_timer_set_next_event; | 197 | ce->set_next_event = sirfsoc_timer_set_next_event; |
198 | clockevents_calc_mult_shift(ce, MARCO_CLOCK_FREQ, 60); | 198 | clockevents_calc_mult_shift(ce, marco_timer_rate, 60); |
199 | ce->max_delta_ns = clockevent_delta2ns(-2, ce); | 199 | ce->max_delta_ns = clockevent_delta2ns(-2, ce); |
200 | ce->min_delta_ns = clockevent_delta2ns(2, ce); | 200 | ce->min_delta_ns = clockevent_delta2ns(2, ce); |
201 | ce->cpumask = cpumask_of(cpu); | 201 | ce->cpumask = cpumask_of(cpu); |
@@ -257,7 +257,6 @@ static void __init sirfsoc_clockevent_init(void) | |||
257 | /* initialize the kernel jiffy timer source */ | 257 | /* initialize the kernel jiffy timer source */ |
258 | static void __init sirfsoc_marco_timer_init(struct device_node *np) | 258 | static void __init sirfsoc_marco_timer_init(struct device_node *np) |
259 | { | 259 | { |
260 | unsigned long rate; | ||
261 | u32 timer_div; | 260 | u32 timer_div; |
262 | struct clk *clk; | 261 | struct clk *clk; |
263 | 262 | ||
@@ -266,16 +265,12 @@ static void __init sirfsoc_marco_timer_init(struct device_node *np) | |||
266 | 265 | ||
267 | BUG_ON(clk_prepare_enable(clk)); | 266 | BUG_ON(clk_prepare_enable(clk)); |
268 | 267 | ||
269 | rate = clk_get_rate(clk); | 268 | marco_timer_rate = clk_get_rate(clk); |
270 | |||
271 | BUG_ON(rate < MARCO_CLOCK_FREQ); | ||
272 | BUG_ON(rate % MARCO_CLOCK_FREQ); | ||
273 | 269 | ||
274 | /* Initialize the timer dividers */ | 270 | /* timer dividers: 0, not divided */ |
275 | timer_div = rate / MARCO_CLOCK_FREQ - 1; | 271 | writel_relaxed(0, sirfsoc_timer_base + SIRFSOC_TIMER_64COUNTER_CTRL); |
276 | writel_relaxed(timer_div << 16, sirfsoc_timer_base + SIRFSOC_TIMER_64COUNTER_CTRL); | 272 | writel_relaxed(0, sirfsoc_timer_base + SIRFSOC_TIMER_32COUNTER_0_CTRL); |
277 | writel_relaxed(timer_div << 16, sirfsoc_timer_base + SIRFSOC_TIMER_32COUNTER_0_CTRL); | 273 | writel_relaxed(0, sirfsoc_timer_base + SIRFSOC_TIMER_32COUNTER_1_CTRL); |
278 | writel_relaxed(timer_div << 16, sirfsoc_timer_base + SIRFSOC_TIMER_32COUNTER_1_CTRL); | ||
279 | 274 | ||
280 | /* Initialize timer counters to 0 */ | 275 | /* Initialize timer counters to 0 */ |
281 | writel_relaxed(0, sirfsoc_timer_base + SIRFSOC_TIMER_64COUNTER_LOAD_LO); | 276 | writel_relaxed(0, sirfsoc_timer_base + SIRFSOC_TIMER_64COUNTER_LOAD_LO); |
@@ -288,7 +283,7 @@ static void __init sirfsoc_marco_timer_init(struct device_node *np) | |||
288 | /* Clear all interrupts */ | 283 | /* Clear all interrupts */ |
289 | writel_relaxed(0xFFFF, sirfsoc_timer_base + SIRFSOC_TIMER_INTR_STATUS); | 284 | writel_relaxed(0xFFFF, sirfsoc_timer_base + SIRFSOC_TIMER_INTR_STATUS); |
290 | 285 | ||
291 | BUG_ON(clocksource_register_hz(&sirfsoc_clocksource, MARCO_CLOCK_FREQ)); | 286 | BUG_ON(clocksource_register_hz(&sirfsoc_clocksource, marco_timer_rate)); |
292 | 287 | ||
293 | sirfsoc_clockevent_init(); | 288 | sirfsoc_clockevent_init(); |
294 | } | 289 | } |
diff --git a/drivers/watchdog/orion_wdt.c b/drivers/watchdog/orion_wdt.c index 00d0741228fc..8cb1ff3bcd90 100644 --- a/drivers/watchdog/orion_wdt.c +++ b/drivers/watchdog/orion_wdt.c | |||
@@ -114,6 +114,46 @@ static int armada370_wdt_clock_init(struct platform_device *pdev, | |||
114 | return 0; | 114 | return 0; |
115 | } | 115 | } |
116 | 116 | ||
117 | static int armada375_wdt_clock_init(struct platform_device *pdev, | ||
118 | struct orion_watchdog *dev) | ||
119 | { | ||
120 | int ret; | ||
121 | |||
122 | dev->clk = of_clk_get_by_name(pdev->dev.of_node, "fixed"); | ||
123 | if (!IS_ERR(dev->clk)) { | ||
124 | ret = clk_prepare_enable(dev->clk); | ||
125 | if (ret) { | ||
126 | clk_put(dev->clk); | ||
127 | return ret; | ||
128 | } | ||
129 | |||
130 | atomic_io_modify(dev->reg + TIMER_CTRL, | ||
131 | WDT_AXP_FIXED_ENABLE_BIT, | ||
132 | WDT_AXP_FIXED_ENABLE_BIT); | ||
133 | dev->clk_rate = clk_get_rate(dev->clk); | ||
134 | |||
135 | return 0; | ||
136 | } | ||
137 | |||
138 | /* Mandatory fallback for proper devicetree backward compatibility */ | ||
139 | dev->clk = clk_get(&pdev->dev, NULL); | ||
140 | if (IS_ERR(dev->clk)) | ||
141 | return PTR_ERR(dev->clk); | ||
142 | |||
143 | ret = clk_prepare_enable(dev->clk); | ||
144 | if (ret) { | ||
145 | clk_put(dev->clk); | ||
146 | return ret; | ||
147 | } | ||
148 | |||
149 | atomic_io_modify(dev->reg + TIMER_CTRL, | ||
150 | WDT_A370_RATIO_MASK(WDT_A370_RATIO_SHIFT), | ||
151 | WDT_A370_RATIO_MASK(WDT_A370_RATIO_SHIFT)); | ||
152 | dev->clk_rate = clk_get_rate(dev->clk) / WDT_A370_RATIO; | ||
153 | |||
154 | return 0; | ||
155 | } | ||
156 | |||
117 | static int armadaxp_wdt_clock_init(struct platform_device *pdev, | 157 | static int armadaxp_wdt_clock_init(struct platform_device *pdev, |
118 | struct orion_watchdog *dev) | 158 | struct orion_watchdog *dev) |
119 | { | 159 | { |
@@ -394,7 +434,7 @@ static const struct orion_watchdog_data armada375_data = { | |||
394 | .rstout_mask_bit = BIT(10), | 434 | .rstout_mask_bit = BIT(10), |
395 | .wdt_enable_bit = BIT(8), | 435 | .wdt_enable_bit = BIT(8), |
396 | .wdt_counter_offset = 0x34, | 436 | .wdt_counter_offset = 0x34, |
397 | .clock_init = armada370_wdt_clock_init, | 437 | .clock_init = armada375_wdt_clock_init, |
398 | .enabled = armada375_enabled, | 438 | .enabled = armada375_enabled, |
399 | .start = armada375_start, | 439 | .start = armada375_start, |
400 | .stop = armada375_stop, | 440 | .stop = armada375_stop, |