diff options
author | Russell King <rmk+kernel@arm.linux.org.uk> | 2012-10-04 18:02:26 -0400 |
---|---|---|
committer | Russell King <rmk+kernel@arm.linux.org.uk> | 2012-10-04 18:02:26 -0400 |
commit | ceaa1a13c0e53242555fa45887d82339a3f93c78 (patch) | |
tree | 665bebcd325c68a1424a49baf9be52512b2d8aa1 /arch/arm/lib | |
parent | ba4a63f89c8f8a014450e45fd96a06a5e078e52f (diff) | |
parent | 56942fec06efa0e17df0f4c3b438332c923b9014 (diff) |
Merge branch 'arch-timers' into for-linus
Conflicts:
arch/arm/include/asm/timex.h
arch/arm/lib/delay.c
Diffstat (limited to 'arch/arm/lib')
-rw-r--r-- | arch/arm/lib/delay.c | 35 |
1 files changed, 26 insertions, 9 deletions
diff --git a/arch/arm/lib/delay.c b/arch/arm/lib/delay.c index 395d5fbb8fa2..9d0a30032d7f 100644 --- a/arch/arm/lib/delay.c +++ b/arch/arm/lib/delay.c | |||
@@ -34,7 +34,18 @@ struct arm_delay_ops arm_delay_ops = { | |||
34 | .udelay = __loop_udelay, | 34 | .udelay = __loop_udelay, |
35 | }; | 35 | }; |
36 | 36 | ||
37 | #ifdef ARCH_HAS_READ_CURRENT_TIMER | 37 | static const struct delay_timer *delay_timer; |
38 | static bool delay_calibrated; | ||
39 | |||
40 | int read_current_timer(unsigned long *timer_val) | ||
41 | { | ||
42 | if (!delay_timer) | ||
43 | return -ENXIO; | ||
44 | |||
45 | *timer_val = delay_timer->read_current_timer(); | ||
46 | return 0; | ||
47 | } | ||
48 | |||
38 | static void __timer_delay(unsigned long cycles) | 49 | static void __timer_delay(unsigned long cycles) |
39 | { | 50 | { |
40 | cycles_t start = get_cycles(); | 51 | cycles_t start = get_cycles(); |
@@ -55,18 +66,24 @@ static void __timer_udelay(unsigned long usecs) | |||
55 | __timer_const_udelay(usecs * UDELAY_MULT); | 66 | __timer_const_udelay(usecs * UDELAY_MULT); |
56 | } | 67 | } |
57 | 68 | ||
58 | void __init init_current_timer_delay(unsigned long freq) | 69 | void __init register_current_timer_delay(const struct delay_timer *timer) |
59 | { | 70 | { |
60 | pr_info("Switching to timer-based delay loop\n"); | 71 | if (!delay_calibrated) { |
61 | lpj_fine = freq / HZ; | 72 | pr_info("Switching to timer-based delay loop\n"); |
62 | loops_per_jiffy = lpj_fine; | 73 | delay_timer = timer; |
63 | arm_delay_ops.delay = __timer_delay; | 74 | lpj_fine = timer->freq / HZ; |
64 | arm_delay_ops.const_udelay = __timer_const_udelay; | 75 | loops_per_jiffy = lpj_fine; |
65 | arm_delay_ops.udelay = __timer_udelay; | 76 | arm_delay_ops.delay = __timer_delay; |
77 | arm_delay_ops.const_udelay = __timer_const_udelay; | ||
78 | arm_delay_ops.udelay = __timer_udelay; | ||
79 | delay_calibrated = true; | ||
80 | } else { | ||
81 | pr_info("Ignoring duplicate/late registration of read_current_timer delay\n"); | ||
82 | } | ||
66 | } | 83 | } |
67 | 84 | ||
68 | unsigned long __cpuinit calibrate_delay_is_known(void) | 85 | unsigned long __cpuinit calibrate_delay_is_known(void) |
69 | { | 86 | { |
87 | delay_calibrated = true; | ||
70 | return lpj_fine; | 88 | return lpj_fine; |
71 | } | 89 | } |
72 | #endif | ||