iPod Classic: minor modifications in TIMER

The current behaviour should not change.

Change-Id: Ia8f44cdccf41dbc3881722f9aebab91de51a9bc5
This commit is contained in:
Cástor Muñoz 2014-12-01 02:33:41 +01:00
parent 8618f2c227
commit bfb63f8017
3 changed files with 24 additions and 23 deletions

View file

@ -39,19 +39,16 @@ void tick_start(unsigned int interval_in_ms)
{
int cycles = 10 * interval_in_ms;
/* configure timer for 10 kHz (external source) */
/* configure timer for 10 kHz (12 MHz / 16 / 75) */
TBCMD = (1 << 1); /* TB_CLR */
TBPRE = 75 - 1; /* prescaler */ /* 12 MHz / 16 / 75 = 10 KHz */
TBPRE = 75 - 1; /* prescaler */
TBCON = (0 << 13) | /* TB_INT1_EN */
(1 << 12) | /* TB_INT0_EN */
(0 << 11) | /* TB_START */
(2 << 8) | /* TB_CS = PCLK / 16 */
(1 << 6) | /* UNKNOWN bit */ /* external 12 MHz clock (?) */
(2 << 8) | /* TB_CS = ECLK / 16 */
(1 << 6) | /* select ECLK (12 MHz) */
(0 << 4); /* TB_MODE_SEL = interval mode */
TBDATA0 = cycles; /* set interval period */
TBCMD = (1 << 0); /* TB_EN */
/* enable timer interrupt */
VIC0INTENABLE = 1 << IRQ_TIMER;
}

View file

@ -134,7 +134,7 @@ void INT_TIMER32(void) ICODE_ATTR;
void INT_TIMER32()
{
uint32_t tstat = TSTAT;
/*if ((TECON >> 12) & 0x7 & (tstat >> 24)) INT_TIMERE();*/
if ((TECON >> 12) & 0x7 & (tstat >> 24)) INT_TIMERE();
if ((TFCON >> 12) & 0x7 & (tstat >> 16)) INT_TIMERF();
if ((TGCON >> 12) & 0x7 & (tstat >> 8)) INT_TIMERG();
if ((THCON >> 12) & 0x7 & tstat) INT_TIMERH();
@ -226,6 +226,7 @@ void system_init(void)
VIC0INTENABLE = 1 << IRQ_WHEEL;
VIC0INTENABLE = 1 << IRQ_ATA;
VIC1INTENABLE = 1 << (IRQ_MMC - 32);
VIC0INTENABLE = 1 << IRQ_TIMER;
VIC0INTENABLE = 1 << IRQ_TIMER32;
}

View file

@ -38,8 +38,10 @@ void INT_TIMERF(void)
bool timer_set(long cycles, bool start)
{
int tf_en = TFCMD & (1 << 0); /* save TF_EN status */
/* stop timer */
TFCMD = (0 << 0); /* TF_ENABLE */
TFCMD = (0 << 0); /* TF_EN = disable */
/* optionally unregister any previously registered timer user */
if (start) {
@ -49,33 +51,34 @@ bool timer_set(long cycles, bool start)
}
}
/* There is an odd behaviour when the 32-bit timers are launched
for the first time, the interrupt status bits are set and an
unexpected interrupt is generated if they are enabled. A way to
workaround this is to write the data registers before clearing
the counter. */
TFDATA0 = cycles;
TFCMD = (1 << 1); /* TF_CLR */
/* configure timer */
TFCON = (1 << 12) | /* TF_INT0_EN */
(4 << 8) | /* TF_CS, 4 = ECLK / 1 */
(1 << 6) | /* use ECLK (12MHz) */
(0 << 4); /* TF_MODE_SEL, 0 = interval mode */
(4 << 8) | /* TF_CS = ECLK / 1 */
(1 << 6) | /* select ECLK (12 MHz) */
(0 << 4); /* TF_MODE_SEL = interval mode */
TFPRE = 0; /* no prescaler */
TFDATA0 = cycles; /* set interval period */
TFCMD = (1 << 0); /* TF_ENABLE */
/* After the configuration, we must write '1' in TF_CLR to
* initialize the timer (s5l8700 DS):
* - Clear the counter register.
* - The value of TF_START is set to TF_OUT.
* - TF_DATA0 and TF_DATA1 are updated to the internal buffers.
* - Initialize the state of the previously captured signal.
*/
TFCMD = (1 << 1) | /* TF_CLR = initialize timer */
(tf_en << 0); /* TF_EN = restore previous status */
return true;
}
bool timer_start(void)
{
TFCMD = (1 << 0); /* TF_ENABLE */
TFCMD = (1 << 0); /* TF_EN = enable */
return true;
}
void timer_stop(void)
{
TFCMD = (0 << 0); /* TF_ENABLE */
TFCMD = (0 << 0); /* TF_EN = disable */
}