diff options
-rw-r--r-- | arch/m68knommu/platform/68328/timers.c | 56 |
1 files changed, 43 insertions, 13 deletions
diff --git a/arch/m68knommu/platform/68328/timers.c b/arch/m68knommu/platform/68328/timers.c index 04cbc661d4bd..9159fd05c9ac 100644 --- a/arch/m68knommu/platform/68328/timers.c +++ b/arch/m68knommu/platform/68328/timers.c | |||
@@ -19,6 +19,7 @@ | |||
19 | #include <linux/mm.h> | 19 | #include <linux/mm.h> |
20 | #include <linux/interrupt.h> | 20 | #include <linux/interrupt.h> |
21 | #include <linux/irq.h> | 21 | #include <linux/irq.h> |
22 | #include <linux/clocksource.h> | ||
22 | #include <asm/setup.h> | 23 | #include <asm/setup.h> |
23 | #include <asm/system.h> | 24 | #include <asm/system.h> |
24 | #include <asm/pgtable.h> | 25 | #include <asm/pgtable.h> |
@@ -51,6 +52,19 @@ | |||
51 | #define TICKS_PER_JIFFY 10 | 52 | #define TICKS_PER_JIFFY 10 |
52 | #endif | 53 | #endif |
53 | 54 | ||
55 | static u32 m68328_tick_cnt; | ||
56 | |||
57 | /***************************************************************************/ | ||
58 | |||
59 | static irqreturn_t hw_tick(int irq, void *dummy) | ||
60 | { | ||
61 | /* Reset Timer1 */ | ||
62 | TSTAT &= 0; | ||
63 | |||
64 | m68328_tick_cnt += TICKS_PER_JIFFY; | ||
65 | return arch_timer_interrupt(irq, dummy); | ||
66 | } | ||
67 | |||
54 | /***************************************************************************/ | 68 | /***************************************************************************/ |
55 | 69 | ||
56 | static irqreturn_t hw_tick(int irq, void *dummy) | 70 | static irqreturn_t hw_tick(int irq, void *dummy) |
@@ -69,6 +83,33 @@ static struct irqaction m68328_timer_irq = { | |||
69 | .handler = hw_tick, | 83 | .handler = hw_tick, |
70 | }; | 84 | }; |
71 | 85 | ||
86 | /***************************************************************************/ | ||
87 | |||
88 | static cycle_t m68328_read_clk(void) | ||
89 | { | ||
90 | unsigned long flags; | ||
91 | u32 cycles; | ||
92 | |||
93 | local_irq_save(flags); | ||
94 | cycles = m68328_tick_cnt + TCN; | ||
95 | local_irq_restore(flags); | ||
96 | |||
97 | return cycles; | ||
98 | } | ||
99 | |||
100 | /***************************************************************************/ | ||
101 | |||
102 | static struct clocksource m68328_clk = { | ||
103 | .name = "timer", | ||
104 | .rating = 250, | ||
105 | .read = m68328_read_clk, | ||
106 | .shift = 20, | ||
107 | .mask = CLOCKSOURCE_MASK(32), | ||
108 | .flags = CLOCK_SOURCE_IS_CONTINUOUS, | ||
109 | }; | ||
110 | |||
111 | /***************************************************************************/ | ||
112 | |||
72 | void hw_timer_init(void) | 113 | void hw_timer_init(void) |
73 | { | 114 | { |
74 | /* disable timer 1 */ | 115 | /* disable timer 1 */ |
@@ -84,19 +125,8 @@ void hw_timer_init(void) | |||
84 | 125 | ||
85 | /* Enable timer 1 */ | 126 | /* Enable timer 1 */ |
86 | TCTL |= TCTL_TEN; | 127 | TCTL |= TCTL_TEN; |
87 | } | 128 | m68328_clk.mult = clocksource_hz2mult(TICKS_PER_JIFFY*HZ, m68328_clk.shift); |
88 | 129 | clocksource_register(&m68328_clk); | |
89 | /***************************************************************************/ | ||
90 | |||
91 | unsigned long hw_timer_offset(void) | ||
92 | { | ||
93 | unsigned long ticks = TCN, offset = 0; | ||
94 | |||
95 | /* check for pending interrupt */ | ||
96 | if (ticks < (TICKS_PER_JIFFY >> 1) && (ISR & (1 << TMR_IRQ_NUM))) | ||
97 | offset = 1000000 / HZ; | ||
98 | ticks = (ticks * 1000000 / HZ) / TICKS_PER_JIFFY; | ||
99 | return ticks + offset; | ||
100 | } | 130 | } |
101 | 131 | ||
102 | /***************************************************************************/ | 132 | /***************************************************************************/ |