Fix timer bugs

Former-commit-id: 9839368895dca306b66a095ab0b9386c77bd2c12
This commit is contained in:
Michel Heily 2019-08-07 09:44:47 +03:00
parent c72bbb96fd
commit fe071bf1ec
2 changed files with 24 additions and 16 deletions

View file

@ -237,19 +237,19 @@ impl Bus for IoRegs {
REG_TM1CNT_L => { REG_TM1CNT_L => {
io.timers[1].timer_data = value; io.timers[1].timer_data = value;
io.timers[0].initial_data = value; io.timers[1].initial_data = value;
} }
REG_TM1CNT_H => io.timers[1].timer_ctl.0 = value, REG_TM1CNT_H => io.timers[1].timer_ctl.0 = value,
REG_TM2CNT_L => { REG_TM2CNT_L => {
io.timers[2].timer_data = value; io.timers[2].timer_data = value;
io.timers[0].initial_data = value; io.timers[2].initial_data = value;
} }
REG_TM2CNT_H => io.timers[2].timer_ctl.0 = value, REG_TM2CNT_H => io.timers[2].timer_ctl.0 = value,
REG_TM3CNT_L => { REG_TM3CNT_L => {
io.timers[3].timer_data = value; io.timers[3].timer_data = value;
io.timers[0].initial_data = value; io.timers[3].initial_data = value;
} }
REG_TM3CNT_H => io.timers[3].timer_ctl.0 = value, REG_TM3CNT_H => io.timers[3].timer_ctl.0 = value,

View file

@ -20,7 +20,7 @@ pub struct Timer {
} }
pub enum TimerAction { pub enum TimerAction {
Overflow, Overflow(usize),
Increment, Increment,
} }
@ -50,6 +50,7 @@ impl Timer {
} }
pub fn add_cycles(&mut self, cycles: usize, irqs: &mut IrqBitmask) -> TimerAction { pub fn add_cycles(&mut self, cycles: usize, irqs: &mut IrqBitmask) -> TimerAction {
let mut num_overflows = 0;
self.cycles += cycles; self.cycles += cycles;
let frequency = self.frequency(); let frequency = self.frequency();
@ -60,12 +61,15 @@ impl Timer {
if self.timer_ctl.irq_enabled() { if self.timer_ctl.irq_enabled() {
irqs.add_irq(self.get_irq()); irqs.add_irq(self.get_irq());
} }
println!("timer{} overflow", self.timer_id); self.timer_data = self.initial_data;
return TimerAction::Overflow; num_overflows += 1;
} }
} }
if num_overflows > 0 {
return TimerAction::Increment; return TimerAction::Overflow(num_overflows);
} else {
return TimerAction::Increment;
}
} }
} }
@ -96,16 +100,20 @@ impl SyncedIoDevice for Timers {
for i in 0..4 { for i in 0..4 {
if self[i].timer_ctl.enabled() && !self[i].timer_ctl.cascade() { if self[i].timer_ctl.enabled() && !self[i].timer_ctl.cascade() {
match self[i].add_cycles(cycles, irqs) { match self[i].add_cycles(cycles, irqs) {
TimerAction::Overflow => match i { TimerAction::Overflow(num_overflows) => {
3 => {} println!("timer{} overflowed {} times", i, num_overflows);
_ => { match i {
let next_i = i +1; 3 => {}
if self[next_i].timer_ctl.cascade() { _ => {
println!("{:?} is cascade!", self[next_i]); let next_i = i + 1;
self[next_i].add_cycles(1, irqs); if self[next_i].timer_ctl.cascade() {
println!("cascading into timer{}", next_i);
self[next_i].add_cycles(num_overflows, irqs);
}
} }
} }
}, }
TimerAction::Increment => {}
_ => {} _ => {}
} }
} }