/** * Reset ST emulator states, chips, interrupts and registers. * Return zero or negative TOS image load error code. */ static const char* Reset_ST(bool bCold) { if (bCold) { const char* error_str; error_str=memory_init(ConfigureParams.Memory.nMemoryBankSize); if (error_str!=NULL) { return error_str; } } CycInt_Reset(); /* Reset interrupts */ Video_Reset(); /* Reset video */ TMC_Reset(); /* Reset TMC Registers */ SCR_Reset(); /* Reset System Control Registers */ nvram_init(); /* Reset NVRAM */ SCSI_Reset(); /* Reset SCSI disks */ MO_Reset(); /* Reset MO disks */ Floppy_Reset(); /* Reset Floppy disks */ SCC_Reset(2); /* Reset SCC */ Ethernet_Reset(true); /* Reset Ethernet */ Sound_Reset(); /* Reset Sound */ Screen_Reset(); /* Reset screen */ DSP_Reset(); /* Reset DSP */ M68000_Reset(bCold); /* Reset CPU */ DebugCpu_SetDebugging(); /* Re-set debugging flag if needed */ return NULL; }
/** * Save/Restore snapshot of CPU variables ('MemorySnapShot_Store' handles type) */ void DSP_MemorySnapShot_Capture(bool bSave) { #if ENABLE_DSP_EMU if (!bSave) DSP_Reset(); MemorySnapShot_Store(&bDspEnabled, sizeof(bDspEnabled)); MemorySnapShot_Store(&dsp_core, sizeof(dsp_core)); MemorySnapShot_Store(&save_cycles, sizeof(save_cycles)); #endif }
/** * Write byte to YM's register (0xff8802), store according to PSG select register (0xff8800) */ void PSG_Set_DataRegister(Uint8 val) { if (LOG_TRACE_LEVEL(TRACE_PSG_WRITE)) { int FrameCycles, HblCounterVideo, LineCycles; Video_GetPosition ( &FrameCycles , &HblCounterVideo , &LineCycles ); LOG_TRACE_PRINT("ym write data reg=0x%x val=0x%x video_cyc=%d %d@%d pc=%x instr_cycle %d\n", PSGRegisterSelect, val, FrameCycles, LineCycles, HblCounterVideo, M68000_GetPC(), CurrentInstrCycles); } /* Is a valid PSG register currently selected ? */ if ( PSGRegisterSelect >= MAX_PSG_REGISTERS ) return; /* not valid, ignore write and do nothing */ /* Create samples up until this point with current values */ Sound_Update(false); /* When a read is made from $ff8800 without changing PSGRegisterSelect, we should return */ /* the non masked value. */ PSGRegisterReadData = val; /* store non masked value for PSG_Get_DataRegister */ /* Copy value to PSGRegisters[] */ PSGRegisters[PSGRegisterSelect] = val; /* Clear unused bits for some regs */ if ( ( PSGRegisterSelect == PSG_REG_CHANNEL_A_COARSE ) || ( PSGRegisterSelect == PSG_REG_CHANNEL_B_COARSE ) || ( PSGRegisterSelect == PSG_REG_CHANNEL_C_COARSE ) || ( PSGRegisterSelect == PSG_REG_ENV_SHAPE ) ) PSGRegisters[PSGRegisterSelect] &= 0x0f; /* only keep bits 0 - 3 */ else if ( ( PSGRegisterSelect == PSG_REG_CHANNEL_A_AMP ) || ( PSGRegisterSelect == PSG_REG_CHANNEL_B_AMP ) || ( PSGRegisterSelect == PSG_REG_CHANNEL_C_AMP ) || ( PSGRegisterSelect == PSG_REG_NOISE_GENERATOR ) ) PSGRegisters[PSGRegisterSelect] &= 0x1f; /* only keep bits 0 - 4 */ if ( PSGRegisterSelect < NUM_PSG_SOUND_REGISTERS ) { /* Copy sound related registers 0..13 to the sound module's internal buffer */ Sound_WriteReg ( PSGRegisterSelect , PSGRegisters[PSGRegisterSelect] ); } else if ( PSGRegisterSelect == PSG_REG_IO_PORTA ) { /* * FIXME: This is only a prelimary dirty hack! * Port B (Printer port) - writing here needs to be dispatched to the printer * STROBE (Port A bit5) does a short LOW and back to HIGH when the char is valid * To print you need to write the character byte to IOB and you need to toggle STROBE * (like EmuTOS does). */ /* Printer dispatching only when printing is activated */ if (ConfigureParams.Printer.bEnablePrinting) { /* Bit 5 - Centronics strobe? If STROBE is low and the LastStrobe was high, then print/transfer to the emulated Centronics port. */ if (LastStrobe && ( (PSGRegisters[PSG_REG_IO_PORTA]&(1<<5)) == 0 )) { /* Seems like we want to print something... */ Printer_TransferByteTo(PSGRegisters[PSG_REG_IO_PORTB]); /* Initiate a possible GPIP0 Printer BUSY interrupt */ MFP_InputOnChannel ( MFP_INT_GPIP0 , 0 ); /* Initiate a possible GPIP1 Falcon ACK interrupt */ if (ConfigureParams.System.nMachineType == MACHINE_FALCON) MFP_InputOnChannel ( MFP_INT_GPIP1 , 0 ); } } LastStrobe = PSGRegisters[PSG_REG_IO_PORTA]&(1<<5); /* Bit 0-2 : side and drive select */ if ( (PSGRegisters[PSG_REG_IO_PORTA]&(1<<1)) == 0 ) { /* floppy drive A is ON */ Statusbar_SetFloppyLed(DRIVE_LED_A, LED_STATE_ON); } else { Statusbar_SetFloppyLed(DRIVE_LED_A, LED_STATE_OFF); } if ( (PSGRegisters[PSG_REG_IO_PORTA]&(1<<2)) == 0 ) { /* floppy drive B is ON */ Statusbar_SetFloppyLed(DRIVE_LED_B, LED_STATE_ON); } else { Statusbar_SetFloppyLed(DRIVE_LED_B, LED_STATE_OFF); } /* Bit 3 - Centronics as input */ if(PSGRegisters[PSG_REG_IO_PORTA]&(1<<3)) { /* FIXME: might be needed if we want to emulate sound sampling hardware */ } /* handle Falcon specific bits in PORTA of the PSG */ if (ConfigureParams.System.nMachineType == MACHINE_FALCON) { /* Bit 4 - DSP reset? */ if(PSGRegisters[PSG_REG_IO_PORTA]&(1<<4)) { Log_Printf(LOG_DEBUG, "Calling DSP_Reset?\n"); #if ENABLE_DSP_EMU if (ConfigureParams.System.nDSPType == DSP_TYPE_EMU) { DSP_Reset(); } #endif } /* Bit 6 - Internal Speaker control */ if(PSGRegisters[PSG_REG_IO_PORTA]&(1<<6)) { /*Log_Printf(LOG_DEBUG, "Falcon: Internal Speaker state\n");*/ /* FIXME: add code to handle? (if we want to emulate the speaker at all? */ } /* Bit 7 - Reset IDE? */ if(PSGRegisters[PSG_REG_IO_PORTA]&(1<<7)) { Log_Printf(LOG_DEBUG, "Falcon: Reset IDE subsystem\n"); /* FIXME: add code to handle IDE reset */ } } } }
/** * Reset ST emulator states, chips, interrupts and registers. * Return zero or negative TOS image load error code. */ static int Reset_ST(bool bCold) { if (bCold) { int ret; Floppy_GetBootDrive(); /* Find which device to boot from (A: or C:) */ ret = TOS_LoadImage(); /* Load TOS, writes into cartridge memory */ if (ret) return ret; /* If we can not load a TOS image, return now! */ Cart_ResetImage(); /* Load cartridge program into ROM memory. */ Cart_Patch(); } CycInt_Reset(); /* Reset interrupts */ MFP_Reset(); /* Setup MFP chip */ Video_Reset(); /* Reset video */ VDI_Reset(); /* Reset internal VDI variables */ NvRam_Reset(); /* reset NvRAM (video) settings */ GemDOS_Reset(); /* Reset GEMDOS emulation */ if (bCold) { FDC_Reset( bCold ); /* Reset FDC */ } Floppy_Reset(); /* Reset Floppy */ if (ConfigureParams.System.nMachineType == MACHINE_FALCON || ConfigureParams.System.nMachineType == MACHINE_TT) { Ncr5380_Reset(); } if (ConfigureParams.System.nMachineType == MACHINE_FALCON) { DSP_Reset(); /* Reset the DSP */ Crossbar_Reset(bCold); /* Reset Crossbar sound */ } else DmaSnd_Reset(bCold); /* Reset DMA sound */ PSG_Reset(); /* Reset PSG */ Sound_Reset(); /* Reset Sound */ ACIA_Reset( ACIA_Array ); /* ACIA */ IKBD_Reset(bCold); /* Keyboard (after ACIA) */ if (ConfigureParams.System.nMachineType == MACHINE_FALCON && !bUseVDIRes) VIDEL_reset(); else Screen_Reset(); /* Reset screen */ M68000_Reset(bCold); /* Reset CPU */ DebugCpu_SetDebugging(); /* Re-set debugging flag if needed */ DebugDsp_SetDebugging(); Midi_Reset(); #if defined(__linux__) nf_scsidrv_reset(); #endif /* Start HBL, Timer B and VBL interrupts with a 0 cycle delay */ Video_StartInterrupts( 0 ); return 0; }