void y8950LoadState(Y8950* y8950) { SaveState* state = saveStateOpenForRead("msxaudio1"); y8950->address = (UInt8)saveStateGet(state, "address", 0); y8950->timerValue1 = saveStateGet(state, "timerValue1", 0); y8950->timeout1 = saveStateGet(state, "timeout1", 0); y8950->timerRunning1 = saveStateGet(state, "timerRunning1", 0); y8950->timerValue2 = saveStateGet(state, "timerValue2", 0); y8950->timerRunning2 = saveStateGet(state, "timerRunning2", 0); y8950->timeout2 = saveStateGet(state, "timeout2", 0); outd = saveStateGet(state, "outd", 0); ams = saveStateGet(state, "ams", 0); vib = saveStateGet(state, "vib", 0); feedback2 = saveStateGet(state, "feedback2", 0); saveStateClose(state); Y8950LoadState(y8950->opl); YM_DELTAT_ADPCM_LoadState(y8950->opl->deltat); if (y8950->timerRunning1) { boardTimerAdd(y8950->timer1, y8950->timeout1); } if (y8950->timerRunning2) { boardTimerAdd(y8950->timer2, y8950->timeout2); } }
void ym2151LoadState(YM2151* ym2151) { SaveState* state = saveStateOpenForRead("ym2151"); ym2151->address = (UInt8)saveStateGet(state, "address", 0); ym2151->latch = (UInt8)saveStateGet(state, "latch", 0); ym2151->timerValue1 = saveStateGet(state, "timerValue1", 0); ym2151->timerRunning1 = saveStateGet(state, "timerRunning1", 0); ym2151->timeout1 = saveStateGet(state, "timeout1", 0); ym2151->timerValue2 = saveStateGet(state, "timerValue2", 0); ym2151->timerRunning2 = saveStateGet(state, "timerRunning2", 0); ym2151->timeout2 = saveStateGet(state, "timeout2", 0); ym2151->irqVector = (UInt8)saveStateGet(state, "irqVector", 0); saveStateClose(state); YM2151LoadState(ym2151->opl); if (ym2151->timerRunning1) { boardTimerAdd(ym2151->timer1, ym2151->timeout1); } if (ym2151->timerRunning2) { boardTimerAdd(ym2151->timer2, ym2151->timeout2); } }
void moonsoundTimerStart(void* ref, int timer, int start, UInt8 timerRef) { Moonsound* moonsound = (Moonsound*)ref; if (timer == 1) { moonsound->timerRef1 = timerRef; moonsound->timerStarted1 = start; if (start) { moonsound->timeout1 = boardCalcRelativeTimeout(12380, moonsound->timerValue1); boardTimerAdd(moonsound->timer1, moonsound->timeout1); } else { boardTimerRemove(moonsound->timer1); } } else { moonsound->timerRef2 = timerRef; moonsound->timerStarted2 = start; if (start) { moonsound->timeout2 = boardCalcRelativeTimeout(12380, moonsound->timerValue2); boardTimerAdd(moonsound->timer2, moonsound->timeout2); } else { boardTimerRemove(moonsound->timer2); } } }
void moonsoundLoadState(Moonsound* moonsound) { SaveState* state = saveStateOpenForRead("moonsound"); moonsound->timerValue1 = saveStateGet(state, "timerValue1", 0); moonsound->timeout1 = saveStateGet(state, "timeout1", 0); moonsound->timerStarted1 = saveStateGet(state, "timerStarted1", 0); moonsound->timerRef1 = (UInt8)saveStateGet(state, "timerRef1", 0); moonsound->timerValue2 = saveStateGet(state, "timerValue2", 0); moonsound->timeout2 = saveStateGet(state, "timeout2", 0); moonsound->timerStarted2 = saveStateGet(state, "timerStarted2", 0); moonsound->timerRef2 = (UInt8)saveStateGet(state, "timerRef2", 0); moonsound->opl3latch = saveStateGet(state, "opl3latch", 0); moonsound->opl4latch = (UInt8)saveStateGet(state, "opl4latch", 0); saveStateClose(state); moonsound->ymf262->loadState(); moonsound->ymf278->loadState(); if (moonsound->timerStarted1) { boardTimerAdd(moonsound->timer1, moonsound->timeout1); } if (moonsound->timerStarted2) { boardTimerAdd(moonsound->timer2, moonsound->timeout2); } }
static void onRecv(YM2148* midi, UInt32 time) { midi->timeRecv = 0; if (midi->status & STAT_RXRDY) { midi->status |= STAT_OE; if (midi->command & CMD_RSTER) { ym2148Reset(midi); return; } } if (midi->rxPending != 0) { archSemaphoreWait(midi->semaphore, -1); midi->rxData = midi->rxQueue[(midi->rxHead - midi->rxPending) & (RX_QUEUE_SIZE - 1)]; midi->rxPending--; archSemaphoreSignal(midi->semaphore); midi->status |= STAT_RXRDY; if (midi->command & CMD_RDINT) { boardSetDataBus(midi->vector, 0, 0); boardSetInt(0x800); midi->status |= ST_INT; } } midi->timeRecv = boardSystemTime() + midi->charTime; boardTimerAdd(midi->timerRecv, midi->timeRecv); }
static void boardPeriodicCallback(void* ref, UInt32 time) { if (periodicCb != NULL) { periodicCb(periodicRef, time); boardTimerAdd(periodicTimer, time + periodicInterval); } }
void boardCaptureInit() { cap.timer = boardTimerCreate(boardTimerCb, NULL); if (cap.state == CAPTURE_REC) { boardTimerAdd(cap.timer, boardSystemTime() + 1); } }
static void boardTimerCb(void* dummy, UInt32 time) { if (cap.state == CAPTURE_PLAY) { // If we reached the end time +/- 2 seconds we know we should stop // the capture. If not, we restart the timer 1/4 of max time into // the future. (Enventually we'll hit the real end time // This is an ugly workaround for the internal timers short timespan // (~3 minutes). Using the 64 bit timer we can extend the capture to // 90 days. // Will work correct with 'real' 64 bit timers boardSystemTime64(); // Sync clock if (boardCaptureCompleteAmount() < 1000) { boardTimerAdd(cap.timer, time + 0x40000000); } else { actionEmuTogglePause(); cap.state = CAPTURE_IDLE; } } if (cap.state == CAPTURE_REC) { cap.state = CAPTURE_IDLE; boardCaptureStart(cap.filename); } }
void ym2151TimerStart(void* ptr, int timer, int start) { YM2151* ym2151 = (YM2151*)ptr; if (timer == 0) { if (start != 0) { if (!ym2151->timerRunning1) { UInt32 systemTime = boardSystemTime(); UInt32 adjust = systemTime % TIMER_FREQUENCY; ym2151->timeout1 = systemTime + TIMER_FREQUENCY * ym2151->timerValue1 - adjust; boardTimerAdd(ym2151->timer1, ym2151->timeout1); ym2151->timerRunning1 = 1; } } else { if (ym2151->timerRunning1) { boardTimerRemove(ym2151->timer1); ym2151->timerRunning1 = 0; } } } else { if (start != 0) { if (!ym2151->timerRunning2) { UInt32 systemTime = boardSystemTime(); UInt32 adjust = systemTime % (16 * TIMER_FREQUENCY); ym2151->timeout2 = systemTime + TIMER_FREQUENCY * ym2151->timerValue2 - adjust; boardTimerAdd(ym2151->timer2, ym2151->timeout2); ym2151->timerRunning2 = 1; } } else { if (ym2151->timerRunning2) { boardTimerRemove(ym2151->timer2); ym2151->timerRunning2 = 0; } } } }
static YM2148* ym2148Create() { YM2148* midi = (YM2148*)calloc(1, sizeof(YM2148)); midi->midiIo = midiIoCreate(midiInCallback, midi); midi->semaphore = archSemaphoreCreate(1); midi->timerRecv = boardTimerCreate(onRecv, midi); midi->timerTrans = boardTimerCreate(onTrans, midi); midi->timeRecv = boardSystemTime() + midi->charTime; boardTimerAdd(midi->timerRecv, midi->timeRecv); return midi; }
void philipsMidiReset(PhilipsMidi* midi) { midi->status = STAT_TXEMPTY; midi->txPending = 0; midi->rxPending = 0; midi->command = 0; midi->timeRecv = 0; midi->timeTrans = 0; midi->charTime = 10 * boardFrequency() / 31250; boardTimerRemove(midi->timerRecv); boardTimerRemove(midi->timerTrans); midi->timeRecv = boardSystemTime() + midi->charTime; boardTimerAdd(midi->timerRecv, midi->timeRecv); }
void philipsMidiWriteData(PhilipsMidi* midi, UInt8 value) { if (!(midi->status & STAT_TXEMPTY)) { return; } if (midi->txPending == 0) { midiIoTransmit(midi->midiIo, value); midi->timeTrans = boardSystemTime() + midi->charTime; boardTimerAdd(midi->timerTrans, midi->timeTrans); midi->txPending = 1; } else { midi->status &= ~STAT_TXEMPTY; midi->txBuffer = value; } }
static void ym2148WriteData(YM2148* midi, UInt8 value) { if (!(midi->command & CMD_TXEN)) { return; } if (midi->status & STAT_TXEMPTY) { midi->status &= ~STAT_TXEMPTY; midi->sendByte = value; midi->timeTrans = boardSystemTime() + midi->charTime; boardTimerAdd(midi->timerTrans, midi->timeTrans); } else { midi->sendBuffer = value; midi->status &= ~STAT_TXRDY; } }
static void onTrans(PhilipsMidi* midi, UInt32 time) { midi->timeTrans = 0; if (midi->status & STAT_TXEMPTY) { midi->txPending = 0; } else { midiIoTransmit(midi->midiIo, midi->txBuffer); midi->timeTrans = boardSystemTime() + midi->charTime; boardTimerAdd(midi->timerTrans, midi->timeTrans); midi->status |= STAT_TXEMPTY; if (midi->command & CMD_WRINT) { boardSetInt(0x400); midi->status |= ST_INT; } } }
static void onRecv(PhilipsMidi* midi, UInt32 time) { midi->timeRecv = 0; if (midi->status & STAT_RXRDY) { midi->status |= STAT_OE; } else if (midi->rxPending != 0) { archSemaphoreWait(midi->semaphore, -1); midi->rxData = midi->rxQueue[(midi->rxHead - midi->rxPending) & (RX_QUEUE_SIZE - 1)]; midi->rxPending--; archSemaphoreSignal(midi->semaphore); midi->status |= STAT_RXRDY; if (midi->command & CMD_RDINT) { boardSetInt(0x400); midi->status |= ST_INT; } } midi->timeRecv = boardSystemTime() + midi->charTime; boardTimerAdd(midi->timerRecv, midi->timeRecv); }
static void onTrans(YM2148* midi, UInt32 time) { midi->timeTrans = 0; midiIoTransmit(midi->midiIo, midi->sendByte); if (midi->status & STAT_TXRDY) { midi->status |= STAT_TXEMPTY; if (midi->command & CMD_TXINT) { boardSetDataBus(midi->vector, 0, 0); boardSetInt(0x800); midi->status |= ST_INT; } } else { midi->status |= STAT_TXRDY; midi->status &= ~STAT_TXEMPTY; midi->sendByte = midi->sendBuffer; midi->timeTrans = boardSystemTime() + midi->charTime; boardTimerAdd(midi->timerTrans, midi->timeTrans); } }
static void counterSetTimeout(Counter* counter) { int nextTimeout = 0; int mode = counter->mode; // If counter is disabled, just return if (mode != 1 && mode != 5 && counter->gate == 0) { return; } if (counter->outPhase == 1) { nextTimeout = counter->countingElement - counter->endOutPhase1; } else if (counter->outPhase == 2) { nextTimeout = counter->countingElement - counter->endOutPhase2; } if (nextTimeout != 0) { counter->time = boardSystemTime() + (UInt64)boardFrequency() * nextTimeout / counter->frequency; boardTimerAdd(counter->timer, counter->time); } }
void i8254LoadState(I8254* i8254) { SaveState* state = saveStateOpenForRead("i8254"); i8254->counter1->time = saveStateGet(state, "c1_time", 0); i8254->counter1->countingElement = (UInt16)saveStateGet(state, "c1_countingElement", 0); i8254->counter1->outputLatch = (UInt16)saveStateGet(state, "c1_outputLatch", 0); i8254->counter1->countRegister = (UInt16)saveStateGet(state, "c1_countRegister", 0); i8254->counter1->controlWord = (UInt8)saveStateGet(state, "c1_controlWord", 0); i8254->counter1->statusLatch = (UInt8)saveStateGet(state, "c1_statusLatch", 0); i8254->counter1->outputLatched = saveStateGet(state, "c1_outputLatched", 0); i8254->counter1->statusLatched = saveStateGet(state, "c1_statusLatched", 0); i8254->counter1->readPhase = saveStateGet(state, "c1_readPhase", 0); i8254->counter1->writePhase = saveStateGet(state, "c1_writePhase", 0); i8254->counter1->mode = saveStateGet(state, "c1_mode", 0); i8254->counter1->gate = saveStateGet(state, "c1_gate", 0); i8254->counter1->counterLatched = saveStateGet(state, "c1_counterLatched", 0); i8254->counter1->outputState = saveStateGet(state, "c1_outputState", 0); i8254->counter1->outPhase = saveStateGet(state, "c1_outPhase", 0); i8254->counter1->endOutPhase1 = saveStateGet(state, "c1_endOutPhase1", 0); i8254->counter1->endOutPhase2 = saveStateGet(state, "c1_endOutPhase2", 0); i8254->counter1->insideTimerLoop = saveStateGet(state, "c1_insideTimerLoop", 0); i8254->counter1->frequency = saveStateGet(state, "c1_frequency", 0); i8254->counter1->refTime = saveStateGet(state, "c1_refTime", 0); i8254->counter1->refFrag = saveStateGet(state, "c1_refFrag", 0); i8254->counter2->time = saveStateGet(state, "c2_time", 0); i8254->counter2->countingElement = (UInt16)saveStateGet(state, "c2_countingElement", 0); i8254->counter2->outputLatch = (UInt16)saveStateGet(state, "c2_outputLatch", 0); i8254->counter2->countRegister = (UInt16)saveStateGet(state, "c2_countRegister", 0); i8254->counter2->controlWord = (UInt8)saveStateGet(state, "c2_controlWord", 0); i8254->counter2->statusLatch = (UInt8)saveStateGet(state, "c2_statusLatch", 0); i8254->counter2->outputLatched = saveStateGet(state, "c2_outputLatched", 0); i8254->counter2->statusLatched = saveStateGet(state, "c2_statusLatched", 0); i8254->counter2->readPhase = saveStateGet(state, "c2_readPhase", 0); i8254->counter2->writePhase = saveStateGet(state, "c2_writePhase", 0); i8254->counter2->mode = saveStateGet(state, "c2_mode", 0); i8254->counter2->gate = saveStateGet(state, "c2_gate", 0); i8254->counter2->counterLatched = saveStateGet(state, "c2_counterLatched", 0); i8254->counter2->outputState = saveStateGet(state, "c2_outputState", 0); i8254->counter2->outPhase = saveStateGet(state, "c2_outPhase", 0); i8254->counter2->endOutPhase1 = saveStateGet(state, "c2_endOutPhase1", 0); i8254->counter2->endOutPhase2 = saveStateGet(state, "c2_endOutPhase2", 0); i8254->counter2->insideTimerLoop = saveStateGet(state, "c2_insideTimerLoop", 0); i8254->counter2->frequency = saveStateGet(state, "c2_frequency", 0); i8254->counter2->refTime = saveStateGet(state, "c2_refTime", 0); i8254->counter2->refFrag = saveStateGet(state, "c2_refFrag", 0); i8254->counter3->time = saveStateGet(state, "c3_time", 0); i8254->counter3->countingElement = (UInt16)saveStateGet(state, "c3_countingElement", 0); i8254->counter3->outputLatch = (UInt16)saveStateGet(state, "c3_outputLatch", 0); i8254->counter3->countRegister = (UInt16)saveStateGet(state, "c3_countRegister", 0); i8254->counter3->controlWord = (UInt8)saveStateGet(state, "c3_controlWord", 0); i8254->counter3->statusLatch = (UInt8)saveStateGet(state, "c3_statusLatch", 0); i8254->counter3->outputLatched = saveStateGet(state, "c3_outputLatched", 0); i8254->counter3->statusLatched = saveStateGet(state, "c3_statusLatched", 0); i8254->counter3->readPhase = saveStateGet(state, "c3_readPhase", 0); i8254->counter3->writePhase = saveStateGet(state, "c3_writePhase", 0); i8254->counter3->mode = saveStateGet(state, "c3_mode", 0); i8254->counter3->gate = saveStateGet(state, "c3_gate", 0); i8254->counter3->counterLatched = saveStateGet(state, "c3_counterLatched", 0); i8254->counter3->outputState = saveStateGet(state, "c3_outputState", 0); i8254->counter3->outPhase = saveStateGet(state, "c3_outPhase", 0); i8254->counter3->endOutPhase1 = saveStateGet(state, "c3_endOutPhase1", 0); i8254->counter3->endOutPhase2 = saveStateGet(state, "c3_endOutPhase2", 0); i8254->counter3->insideTimerLoop = saveStateGet(state, "c3_insideTimerLoop", 0); i8254->counter3->frequency = saveStateGet(state, "c3_frequency", 0); i8254->counter3->refTime = saveStateGet(state, "c3_refTime", 0); i8254->counter3->refFrag = saveStateGet(state, "c3_refFrag", 0); if (i8254->counter1->time != 0) { boardTimerAdd(i8254->counter1->timer, i8254->counter1->time); } if (i8254->counter2->time != 0) { boardTimerAdd(i8254->counter2->timer, i8254->counter2->time); } if (i8254->counter3->time != 0) { boardTimerAdd(i8254->counter3->timer, i8254->counter3->time); } saveStateClose(state); }
void philipsMidiWriteCommand(PhilipsMidi* midi, UInt8 value) { int baudrate = 1; int dataBits = 8; int parityEnable = 0; int stopBits = 1; UInt64 charLength; midi->command = value; switch (value & 0x03) { case 0: baudrate = 1; break; case 1: baudrate = 16; break; case 2: baudrate = 64; break; case 3: philipsMidiReset(midi); break; } switch (value & 0x1c) { case 0: dataBits = 7; parityEnable = 1; stopBits = 2; break; case 1: dataBits = 7; parityEnable = 1; stopBits = 2; break; case 2: dataBits = 7; parityEnable = 1; stopBits = 1; break; case 3: dataBits = 7; parityEnable = 1; stopBits = 1; break; case 4: dataBits = 8; parityEnable = 0; stopBits = 2; break; case 5: dataBits = 8; parityEnable = 0; stopBits = 1; break; case 6: dataBits = 8; parityEnable = 0; stopBits = 1; break; case 7: dataBits = 8; parityEnable = 1; stopBits = 1; break; } charLength = (dataBits + parityEnable + stopBits) * baudrate; midi->charTime = (UInt32)(charLength * boardFrequency() / 500000); midi->timeRecv = boardSystemTime() + midi->charTime; boardTimerAdd(midi->timerRecv, midi->timeRecv); }