#ifdef SMP_CPP void SMP::add_clocks(unsigned clocks) { step(clocks); synchronize_dsp(); #if defined(DEBUGGER) #error -DDEBUGGER SMP runtosave() correctness not checked synchronize_cpu(); #else //forcefully sync S-SMP to S-CPU in case chips are not communicating //sync if S-SMP is more than 24 samples ahead of S-CPU /* our new smp design guarantees that there is at most one required synchronize_cpu() per uop, inside an op_busread() or op_buswrite(). this extra synchronize can cause problems if we swap out of the SMP at the beginning of a uop with an add_clocks() call when there is an important op_busread() / op_buswrite() later on. the SMP will need to finish that uop in order to reach a savable state, but it might never get to do so until it's too late (ie, scheduler.sync == Scheduler.SynchronizeMode::All). so we remove this call and instead do catchup sync in the main Enter() loop. */ //if(clock > +(768 * 24 * (int64)24000000)) synchronize_cpu(); #endif } void SMP::cycle_edge() { timer0.tick(); timer1.tick(); timer2.tick(); //TEST register S-SMP speed control //24 clocks have already been added for this cycle at this point switch(status.clock_speed) { case 0: break; //100% speed case 1: add_clocks(24); break; // 50% speed case 2: while(true) add_clocks(24); // 0% speed -- locks S-SMP case 3: add_clocks(24 * 9); break; // 10% speed } } template void SMP::Timer::tick() { //stage 0 increment stage0_ticks += smp.status.timer_step; if(stage0_ticks < timer_frequency) return; stage0_ticks -= timer_frequency; //stage 1 increment stage1_ticks ^= 1; synchronize_stage1(); } template void SMP::Timer::synchronize_stage1() { bool new_line = stage1_ticks; if(smp.status.timers_enable == false) new_line = false; if(smp.status.timers_disable == true) new_line = false; bool old_line = current_line; current_line = new_line; if(old_line != 1 || new_line != 0) return; //only pulse on 1->0 transition //stage 2 increment if(enable == false) return; if(++stage2_ticks != target) return; //stage 3 increment stage2_ticks = 0; stage3_ticks++; } #endif