summaryrefslogtreecommitdiff
path: root/firmware/timer.c
diff options
context:
space:
mode:
Diffstat (limited to 'firmware/timer.c')
-rw-r--r--firmware/timer.c46
1 files changed, 37 insertions, 9 deletions
diff --git a/firmware/timer.c b/firmware/timer.c
index 7d9c288cdd..54e3dc7ac3 100644
--- a/firmware/timer.c
+++ b/firmware/timer.c
@@ -23,8 +23,6 @@
23#include "system.h" 23#include "system.h"
24#include "timer.h" 24#include "timer.h"
25 25
26#ifndef SIMULATOR
27
28static int timer_prio = -1; 26static int timer_prio = -1;
29static void (*pfn_timer)(void) = NULL; /* timer callback */ 27static void (*pfn_timer)(void) = NULL; /* timer callback */
30static void (*pfn_unregister)(void) = NULL; /* unregister callback */ 28static void (*pfn_unregister)(void) = NULL; /* unregister callback */
@@ -49,6 +47,13 @@ void TIMER1(void)
49 pfn_timer(); 47 pfn_timer();
50 TER1 = 0xff; /* clear all events */ 48 TER1 = 0xff; /* clear all events */
51} 49}
50#elif CONFIG_CPU == PP5020 || CONFIG_CPU == PP5002
51void TIMER2(void)
52{
53 TIMER2_VAL; /* ACK interrupt */
54 if (pfn_timer != NULL)
55 pfn_timer();
56}
52#endif /* CONFIG_CPU */ 57#endif /* CONFIG_CPU */
53 58
54static bool timer_set(long cycles, bool start) 59static bool timer_set(long cycles, bool start)
@@ -57,15 +62,21 @@ static bool timer_set(long cycles, bool start)
57 int prescale = 1; 62 int prescale = 1;
58 63
59#if (CONFIG_CPU==PP5002) || (CONFIG_CPU==PP5020) || (CONFIG_CPU==PNX0101) 64#if (CONFIG_CPU==PP5002) || (CONFIG_CPU==PP5020) || (CONFIG_CPU==PNX0101)
60 /* TODO: Implement for iPod and iFP */ 65 /* TODO: Implement for iPod and iFP (if they have prescaler capabilities) */
61 (void)start;
62 (void)phi; 66 (void)phi;
63#endif 67#endif
64 68
69#if CONFIG_CPU == PNX0101
70 (void)start;
71#endif
72
65#ifdef CPU_COLDFIRE 73#ifdef CPU_COLDFIRE
66 cycles >>= 1; /* the coldfire timer works on busclk == cpuclk/2 */ 74 cycles >>= 1; /* the coldfire timer works on busclk == cpuclk/2 */
67#endif 75#endif
68 76
77/* Don't do this on ipods, we don't know if these platforms have prescaler
78 capabilities on the timer we use. */
79#if CONFIG_CPU != PP5020 && CONFIG_CPU != PP5002
69 while (cycles > 0x10000) 80 while (cycles > 0x10000)
70 { /* work out the smallest prescaler that makes it fit */ 81 { /* work out the smallest prescaler that makes it fit */
71#if CONFIG_CPU == SH7034 82#if CONFIG_CPU == SH7034
@@ -74,6 +85,7 @@ static bool timer_set(long cycles, bool start)
74 prescale *= 2; 85 prescale *= 2;
75 cycles >>= 1; 86 cycles >>= 1;
76 } 87 }
88#endif
77 89
78#if CONFIG_CPU == SH7034 90#if CONFIG_CPU == SH7034
79 if (prescale > 8) 91 if (prescale > 8)
@@ -131,7 +143,20 @@ static bool timer_set(long cycles, bool start)
131 if (start || (TCN1 >= TRR1)) 143 if (start || (TCN1 >= TRR1))
132 TCN1 = 0; /* reset the timer */ 144 TCN1 = 0; /* reset the timer */
133 TER1 = 0xff; /* clear all events */ 145 TER1 = 0xff; /* clear all events */
134 146#elif CONFIG_CPU == PP5020 || CONFIG_CPU == PP5002
147 (void)prescale;
148 if (start)
149 {
150 if (pfn_unregister != NULL)
151 {
152 pfn_unregister();
153 pfn_unregister = NULL;
154 }
155 }
156 TIMER2_CFG = 0x0;
157 TIMER2_VAL;
158 /* enable timer */
159 TIMER2_CFG = 0xc0000000 | cycles;
135#endif /* CONFIG_CPU */ 160#endif /* CONFIG_CPU */
136 return true; 161 return true;
137} 162}
@@ -155,7 +180,7 @@ void timers_adjust_prescale(int multiplier, bool enable_irq)
155} 180}
156#endif 181#endif
157 182
158/* Register a user timer, called every <cycles> CPU_FREQ cycles */ 183/* Register a user timer, called every <cycles> TIMER_FREQ cycles */
159bool timer_register(int reg_prio, void (*unregister_callback)(void), 184bool timer_register(int reg_prio, void (*unregister_callback)(void),
160 long cycles, int int_prio, void (*timer_callback)(void)) 185 long cycles, int int_prio, void (*timer_callback)(void))
161{ 186{
@@ -163,7 +188,7 @@ bool timer_register(int reg_prio, void (*unregister_callback)(void),
163 return false; 188 return false;
164 189
165#if (CONFIG_CPU==PP5002) || (CONFIG_CPU==PP5020) || (CONFIG_CPU==PNX0101) 190#if (CONFIG_CPU==PP5002) || (CONFIG_CPU==PP5020) || (CONFIG_CPU==PNX0101)
166 /* TODO: Implement for iPod and iFP */ 191 /* TODO: Implement for iPod and iFP (if possible) */
167 (void)int_prio; 192 (void)int_prio;
168#endif 193#endif
169 194
@@ -188,8 +213,10 @@ bool timer_register(int reg_prio, void (*unregister_callback)(void),
188 ICR2 = 0x90; /* interrupt on level 4.0 */ 213 ICR2 = 0x90; /* interrupt on level 4.0 */
189 and_l(~(1<<10), &IMR); 214 and_l(~(1<<10), &IMR);
190 TMR1 |= 1; /* start timer */ 215 TMR1 |= 1; /* start timer */
216#elif CONFIG_CPU == PP5020 || CONFIG_CPU == PP5002
217 /* unmask interrupt source */
218 CPU_INT_EN = TIMER2_MASK;
191#endif 219#endif
192
193 return true; 220 return true;
194} 221}
195 222
@@ -206,10 +233,11 @@ void timer_unregister(void)
206#elif defined CPU_COLDFIRE 233#elif defined CPU_COLDFIRE
207 TMR1 = 0; /* disable timer 1 */ 234 TMR1 = 0; /* disable timer 1 */
208 or_l((1<<10), &IMR); /* disable interrupt */ 235 or_l((1<<10), &IMR); /* disable interrupt */
236#elif CONFIG_CPU == PP5020 || CONFIG_CPU == PP5002
237 CPU_INT_CLR = TIMER2_MASK;
209#endif 238#endif
210 pfn_timer = NULL; 239 pfn_timer = NULL;
211 pfn_unregister = NULL; 240 pfn_unregister = NULL;
212 timer_prio = -1; 241 timer_prio = -1;
213} 242}
214 243
215#endif /* !SIMULATOR */