From ee824dc308a92e6ead445646e5c2a876e5eece11 Mon Sep 17 00:00:00 2001 From: alyosha-tas Date: Thu, 9 Nov 2017 09:55:24 -0500 Subject: [PATCH] Oops --- Audio.cs | 213 --------- GBHawk.IDebuggable.cs | 77 ---- GBHawk.IEmulator.cs | 156 ------- GBHawk.IInputPollable.cs | 24 - GBHawk.IMemoryDomains.cs | 56 --- GBHawk.ISaveRam.cs | 26 -- GBHawk.ISettable.cs | 77 ---- GBHawk.IStatable.cs | 102 ----- GBHawk.cs | 223 --------- GBHawkControllerDeck.cs | 76 ---- GBHawkControllers.cs | 68 --- HW_Registers.cs | 283 ------------ Mappers/MapperBase.cs | 40 -- Mappers/Mapper_Camera.cs | 59 --- Mappers/Mapper_Default.cs | 59 --- Mappers/Mapper_HuC1.cs | 59 --- Mappers/Mapper_HuC3.cs | 59 --- Mappers/Mapper_MBC1.cs | 130 ------ Mappers/Mapper_MBC2.cs | 59 --- Mappers/Mapper_MBC3.cs | 59 --- Mappers/Mapper_MBC5.cs | 59 --- Mappers/Mapper_MBC6.cs | 59 --- Mappers/Mapper_MBC7.cs | 59 --- Mappers/Mapper_MMM01.cs | 59 --- Mappers/Mapper_TAMA5.cs | 59 --- Mappers/ReadMe.txt | 3 - MemoryMap.cs | 164 ------- PPU.cs | 922 -------------------------------------- Timer.cs | 175 -------- 29 files changed, 3464 deletions(-) delete mode 100644 Audio.cs delete mode 100644 GBHawk.IDebuggable.cs delete mode 100644 GBHawk.IEmulator.cs delete mode 100644 GBHawk.IInputPollable.cs delete mode 100644 GBHawk.IMemoryDomains.cs delete mode 100644 GBHawk.ISaveRam.cs delete mode 100644 GBHawk.ISettable.cs delete mode 100644 GBHawk.IStatable.cs delete mode 100644 GBHawk.cs delete mode 100644 GBHawkControllerDeck.cs delete mode 100644 GBHawkControllers.cs delete mode 100644 HW_Registers.cs delete mode 100644 Mappers/MapperBase.cs delete mode 100644 Mappers/Mapper_Camera.cs delete mode 100644 Mappers/Mapper_Default.cs delete mode 100644 Mappers/Mapper_HuC1.cs delete mode 100644 Mappers/Mapper_HuC3.cs delete mode 100644 Mappers/Mapper_MBC1.cs delete mode 100644 Mappers/Mapper_MBC2.cs delete mode 100644 Mappers/Mapper_MBC3.cs delete mode 100644 Mappers/Mapper_MBC5.cs delete mode 100644 Mappers/Mapper_MBC6.cs delete mode 100644 Mappers/Mapper_MBC7.cs delete mode 100644 Mappers/Mapper_MMM01.cs delete mode 100644 Mappers/Mapper_TAMA5.cs delete mode 100644 Mappers/ReadMe.txt delete mode 100644 MemoryMap.cs delete mode 100644 PPU.cs delete mode 100644 Timer.cs diff --git a/Audio.cs b/Audio.cs deleted file mode 100644 index 7fcaaca85f..0000000000 --- a/Audio.cs +++ /dev/null @@ -1,213 +0,0 @@ -using System; - -using BizHawk.Common; -using BizHawk.Common.BufferExtensions; -using BizHawk.Emulation.Common; -using BizHawk.Common.NumberExtensions; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Audio Emulation - public class Audio : ISoundProvider - { - public GBHawk Core { get; set; } - - public const int NR10 = 0; - public const int NR11 = 1; - public const int NR12 = 2; - public const int NR13 = 3; - public const int NR14 = 4; - public const int NR21 = 5; - public const int NR22 = 6; - public const int NR23 = 7; - public const int NR24 = 8; - public const int NR30 = 9; - public const int NR31 = 10; - public const int NR32 = 11; - public const int NR33 = 12; - public const int NR34 = 13; - public const int NR41 = 14; - public const int NR42 = 15; - public const int NR43 = 16; - public const int NR44 = 17; - public const int NR50 = 18; - public const int NR51 = 19; - public const int NR52 = 20; - - public static int[] unused_bits = new int[] { 0x80, 0x3F, 0x00, 0xFF, 0xBF, - 0x3F, 0x00, 0xFF, 0xBF, - 0x7F, 0xFF, 0x9F, 0xFF, 0xBF, - 0xFF, 0x00, 0x00, 0xBF, - 0x00, 0x00, 0x70}; - - public byte[] Audio_Regs = new byte[21]; - - public byte[] Wave_RAM = new byte [16]; - - - public byte ReadReg(int addr) - { - byte ret = 0; - - switch (addr) - { - case 0xFF10: ret = (byte)(Audio_Regs[NR10] | unused_bits[NR10]); break; // NR10 (sweep) - case 0xFF11: ret = (byte)(Audio_Regs[NR11] | unused_bits[NR11]); break; // NR11 (sound length / wave pattern duty %) - case 0xFF12: ret = (byte)(Audio_Regs[NR12] | unused_bits[NR12]); break; // NR12 (envelope) - case 0xFF13: ret = (byte)(Audio_Regs[NR13] | unused_bits[NR13]); break; // NR13 (freq low) - case 0xFF14: ret = (byte)(Audio_Regs[NR14] | unused_bits[NR14]); break; // NR14 (freq hi) - case 0xFF16: ret = (byte)(Audio_Regs[NR21] | unused_bits[NR21]); break; // NR21 (sound length / wave pattern duty %) - case 0xFF17: ret = (byte)(Audio_Regs[NR22] | unused_bits[NR22]); break; // NR22 (envelope) - case 0xFF18: ret = (byte)(Audio_Regs[NR23] | unused_bits[NR23]); break; // NR23 (freq low) - case 0xFF19: ret = (byte)(Audio_Regs[NR24] | unused_bits[NR24]); break; // NR24 (freq hi) - case 0xFF1A: ret = (byte)(Audio_Regs[NR30] | unused_bits[NR30]); break; // NR30 (on/off) - case 0xFF1B: ret = (byte)(Audio_Regs[NR31] | unused_bits[NR31]); break; // NR31 (length) - case 0xFF1C: ret = (byte)(Audio_Regs[NR32] | unused_bits[NR32]); break; // NR32 (level output) - case 0xFF1D: ret = (byte)(Audio_Regs[NR33] | unused_bits[NR33]); break; // NR33 (freq low) - case 0xFF1E: ret = (byte)(Audio_Regs[NR34] | unused_bits[NR34]); break; // NR34 (freq hi) - case 0xFF20: ret = (byte)(Audio_Regs[NR41] | unused_bits[NR41]); break; // NR41 (sweep) - case 0xFF21: ret = (byte)(Audio_Regs[NR42] | unused_bits[NR42]); break; // NR42 (sweep) - case 0xFF22: ret = (byte)(Audio_Regs[NR43] | unused_bits[NR43]); break; // NR43 (sweep) - case 0xFF23: ret = (byte)(Audio_Regs[NR44] | unused_bits[NR44]); break; // NR44 (sweep) - case 0xFF24: ret = (byte)(Audio_Regs[NR50] | unused_bits[NR50]); break; // NR50 (sweep) - case 0xFF25: ret = (byte)(Audio_Regs[NR51] | unused_bits[NR51]); break; // NR51 (sweep) - case 0xFF26: ret = (byte)(Audio_Regs[NR52] | unused_bits[NR52]); break; // NR52 (sweep) - - // wave ram table - case 0xFF30: - case 0xFF31: - case 0xFF32: - case 0xFF33: - case 0xFF34: - case 0xFF35: - case 0xFF36: - case 0xFF37: - case 0xFF38: - case 0xFF39: - case 0xFF3A: - case 0xFF3B: - case 0xFF3C: - case 0xFF3D: - case 0xFF3E: - case 0xFF3F: - ret = Wave_RAM[addr & 0x0F]; - break; - - } - - return ret; - } - - public void WriteReg(int addr, byte value) - { - switch (addr) - { - case 0xFF10: Audio_Regs[NR10] = value; break; // NR10 (sweep) - case 0xFF11: Audio_Regs[NR11] = value; break; // NR11 (sound length / wave pattern duty %) - case 0xFF12: Audio_Regs[NR12] = value; break; // NR12 (envelope) - case 0xFF13: Audio_Regs[NR13] = value; break; // NR13 (freq low) - case 0xFF14: Audio_Regs[NR14] = value; break; // NR14 (freq hi) - case 0xFF16: Audio_Regs[NR21] = value; break; // NR21 (sound length / wave pattern duty %) - case 0xFF17: Audio_Regs[NR22] = value; break; // NR22 (envelope) - case 0xFF18: Audio_Regs[NR23] = value; break; // NR23 (freq low) - case 0xFF19: Audio_Regs[NR24] = value; break; // NR24 (freq hi) - case 0xFF1A: Audio_Regs[NR30] = value; break; // NR30 (on/off) - case 0xFF1B: Audio_Regs[NR31] = value; break; // NR31 (length) - case 0xFF1C: Audio_Regs[NR32] = value; break; // NR32 (level output) - case 0xFF1D: Audio_Regs[NR33] = value; break; // NR33 (freq low) - case 0xFF1E: Audio_Regs[NR34] = value; break; // NR34 (freq hi) - case 0xFF20: Audio_Regs[NR41] = value; break; // NR41 (sweep) - case 0xFF21: Audio_Regs[NR42] = value; break; // NR42 (sweep) - case 0xFF22: Audio_Regs[NR43] = value; break; // NR43 (sweep) - case 0xFF23: Audio_Regs[NR44] = value; break; // NR44 (sweep) - case 0xFF24: Audio_Regs[NR50] = value; break; // NR50 (sweep) - case 0xFF25: Audio_Regs[NR51] = value; break; // NR51 (sweep) - case 0xFF26: Audio_Regs[NR52] = value; break; // NR52 (sweep) - - // wave ram table - case 0xFF30: - case 0xFF31: - case 0xFF32: - case 0xFF33: - case 0xFF34: - case 0xFF35: - case 0xFF36: - case 0xFF37: - case 0xFF38: - case 0xFF39: - case 0xFF3A: - case 0xFF3B: - case 0xFF3C: - case 0xFF3D: - case 0xFF3E: - case 0xFF3F: - Wave_RAM[addr & 0x0F] = value; - break; - - } - } - - public void tick() - { - - } - - public void reset() - { - Wave_RAM = new byte[16]; - - Audio_Regs = new byte[21]; - } - - public void SyncState(Serializer ser) - { - ser.Sync("Audio_Regs", ref Audio_Regs, false); - ser.Sync("Wave_Ram", ref Wave_RAM, false); - - } - - #region audio - - public bool CanProvideAsync => false; - - public int _spf; - public int AudioClocks; - - public void SetSyncMode(SyncSoundMode mode) - { - if (mode != SyncSoundMode.Sync) - { - throw new InvalidOperationException("Only Sync mode is supported."); - } - } - - public SyncSoundMode SyncMode => SyncSoundMode.Sync; - - public void GetSamplesSync(out short[] samples, out int nsamp) - { - short[] ret = new short[_spf * 2]; - nsamp = _spf; - GetSamples(ret); - samples = ret; - } - - public void GetSamplesAsync(short[] samples) - { - throw new NotSupportedException("Async is not available"); - } - - public void DiscardSamples() - { - AudioClocks = 0; - } - - // Exposing this as GetSamplesAsync would allow this to provide async sound - // However, it does nothing special for async sound so I don't see a point - private void GetSamples(short[] samples) - { - - } - - #endregion - } -} \ No newline at end of file diff --git a/GBHawk.IDebuggable.cs b/GBHawk.IDebuggable.cs deleted file mode 100644 index 543cecf962..0000000000 --- a/GBHawk.IDebuggable.cs +++ /dev/null @@ -1,77 +0,0 @@ -using System; -using System.Collections.Generic; - -using BizHawk.Emulation.Common; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - public partial class GBHawk : IDebuggable - { - public IDictionary GetCpuFlagsAndRegisters() - { - return new Dictionary - { - /* - ["A"] = cpu.A, - ["X"] = cpu.X, - ["Y"] = cpu.Y, - ["S"] = cpu.S, - ["PC"] = cpu.PC, - ["Flag C"] = cpu.FlagC, - ["Flag Z"] = cpu.FlagZ, - ["Flag I"] = cpu.FlagI, - ["Flag D"] = cpu.FlagD, - ["Flag B"] = cpu.FlagB, - ["Flag V"] = cpu.FlagV, - ["Flag N"] = cpu.FlagN, - ["Flag T"] = cpu.FlagT - */ - }; - } - - public void SetCpuRegister(string register, int value) - { - switch (register) - { - default: - throw new InvalidOperationException(); - case "A": - //cpu.A = (byte)value; - break; - case "X": - //cpu.X = (byte)value; - break; - case "Y": - //cpu.Y = (byte)value; - break; - case "S": - //cpu.S = (byte)value; - break; - case "PC": - //cpu.PC = (ushort)value; - break; - case "Flag I": - //cpu.FlagI = value > 0; - break; - } - } - - public IMemoryCallbackSystem MemoryCallbacks { get; } = new MemoryCallbackSystem(); - - public bool CanStep(StepType type) - { - return false; - } - - [FeatureNotImplemented] - public void Step(StepType type) - { - throw new NotImplementedException(); - } - - public int TotalExecutedCycles - { - get { return cpu.TotalExecutedCycles; } - } - } -} diff --git a/GBHawk.IEmulator.cs b/GBHawk.IEmulator.cs deleted file mode 100644 index 189feb6af7..0000000000 --- a/GBHawk.IEmulator.cs +++ /dev/null @@ -1,156 +0,0 @@ -using BizHawk.Common.NumberExtensions; -using BizHawk.Emulation.Common; -using System; -using System.Collections.Generic; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - public partial class GBHawk : IEmulator, IVideoProvider - { - public IEmulatorServiceProvider ServiceProvider { get; } - - public ControllerDefinition ControllerDefinition => _controllerDeck.Definition; - - public byte controller_state; - public byte controller_state_old; - public bool in_vblank_old; - public bool in_vblank; - public bool vblank_rise; - - public void FrameAdvance(IController controller, bool render, bool rendersound) - { - //Console.WriteLine("-----------------------FRAME-----------------------"); - - if (_tracer.Enabled) - { - cpu.TraceCallback = s => _tracer.Put(s); - } - else - { - cpu.TraceCallback = null; - } - - _frame++; - - if (controller.IsPressed("Power")) - { - // it seems that theMachine.Reset() doesn't clear ram, etc - // this should leave hsram intact but clear most other things - HardReset(); - } - - _islag = true; - - GetControllerState(controller); - - do_frame(); - - if (_islag) - { - _lagcount++; - } - } - - public void do_frame() - { - // gameboy frames can be variable lengths - // we want to end a frame when VBlank turns from false to true - int ticker = 0; - while (!vblank_rise && (ticker < 100000)) - { - audio.tick(); - timer.tick_1(); - ppu.tick(); - - cpu.ExecuteOne(ref REG_FF0F, REG_FFFF); - - timer.tick_2(); - - - if (in_vblank && !in_vblank_old) - { - vblank_rise = true; - } - ticker++; - in_vblank_old = in_vblank; - } - - vblank_rise = false; - } - - public void RunCPUCycle() - { - - } - - public void GetControllerState(IController controller) - { - InputCallbacks.Call(); - controller_state = _controllerDeck.ReadPort1(controller); - - // set interrupt flag if a pin went from high to low - if (controller_state < controller_state_old) - { - if (REG_FFFF.Bit(4)) { cpu.FlagI = true; } - REG_FF0F |= 0x10; - } - - controller_state_old = controller_state; - } - - public void serial_transfer() - { - if (serial_control.Bit(7) && !serial_start_old) - { - serial_start_old = true; - - // transfer out on byte of data - // needs to be modelled - } - } - - public int Frame => _frame; - - public string SystemId => "GB"; - - public bool DeterministicEmulation { get; set; } - - public void ResetCounters() - { - _frame = 0; - _lagcount = 0; - _islag = false; - } - - public CoreComm CoreComm { get; } - - public void Dispose() - { - - } - - - #region Video provider - - public int _frameHz = 60; - - public int[] _vidbuffer; - - public int[] GetVideoBuffer() - { - return _vidbuffer; - } - - public int VirtualWidth => 160; - public int VirtualHeight => 144; - public int BufferWidth => 160; - public int BufferHeight => 144; - public int BackgroundColor => unchecked((int)0xFF000000); - public int VsyncNumerator => _frameHz; - public int VsyncDenominator => 1; - - public static readonly uint[] color_palette = { 0xFFFFFFFF , 0xFFAAAAAA, 0xFF555555, 0xFF000000 }; - - #endregion - } -} diff --git a/GBHawk.IInputPollable.cs b/GBHawk.IInputPollable.cs deleted file mode 100644 index 30af4780c6..0000000000 --- a/GBHawk.IInputPollable.cs +++ /dev/null @@ -1,24 +0,0 @@ -using BizHawk.Emulation.Common; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - public partial class GBHawk : IInputPollable - { - public int LagCount - { - get { return _lagcount; } - set { _lagcount = value; } - } - - public bool IsLagFrame - { - get { return _islag; } - set { _islag = value; } - } - - public IInputCallbackSystem InputCallbacks { get; } = new InputCallbackSystem(); - - public bool _islag = true; - private int _lagcount; - } -} diff --git a/GBHawk.IMemoryDomains.cs b/GBHawk.IMemoryDomains.cs deleted file mode 100644 index aa9ecf8b2e..0000000000 --- a/GBHawk.IMemoryDomains.cs +++ /dev/null @@ -1,56 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; - -using BizHawk.Emulation.Common; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - public partial class GBHawk - { - private IMemoryDomains MemoryDomains; - - public void SetupMemoryDomains() - { - var domains = new List - { - new MemoryDomainDelegate( - "Main RAM", - RAM.Length, - MemoryDomain.Endian.Little, - addr => RAM[addr], - (addr, value) => RAM[addr] = value, - 1), - new MemoryDomainDelegate( - "Zero Page RAM", - ZP_RAM.Length, - MemoryDomain.Endian.Little, - addr => ZP_RAM[addr], - (addr, value) => ZP_RAM[addr] = value, - 1), - new MemoryDomainDelegate( - "System Bus", - 0X10000, - MemoryDomain.Endian.Little, - addr => PeekSystemBus(addr), - (addr, value) => PokeSystemBus(addr, value), - 1) - }; - - MemoryDomains = new MemoryDomainList(domains); - (ServiceProvider as BasicServiceProvider).Register(MemoryDomains); - } - - private byte PeekSystemBus(long addr) - { - ushort addr2 = (ushort)(addr & 0xFFFF); - return ReadMemory(addr2); - } - - private void PokeSystemBus(long addr, byte value) - { - ushort addr2 = (ushort)(addr & 0xFFFF); - WriteMemory(addr2, value); - } - } -} diff --git a/GBHawk.ISaveRam.cs b/GBHawk.ISaveRam.cs deleted file mode 100644 index 5936f9543c..0000000000 --- a/GBHawk.ISaveRam.cs +++ /dev/null @@ -1,26 +0,0 @@ -using System; -using BizHawk.Emulation.Common; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - public partial class GBHawk : ISaveRam - { - public byte[] CloneSaveRam() - { - return (byte[])_sram.Clone(); - } - - public void StoreSaveRam(byte[] data) - { - Buffer.BlockCopy(data, 0, _sram, 0, data.Length); - } - - public bool SaveRamModified - { - get - { - return false; - } - } - } -} diff --git a/GBHawk.ISettable.cs b/GBHawk.ISettable.cs deleted file mode 100644 index 75a267bf62..0000000000 --- a/GBHawk.ISettable.cs +++ /dev/null @@ -1,77 +0,0 @@ -using System; -using System.ComponentModel; - -using Newtonsoft.Json; - -using BizHawk.Common; -using BizHawk.Emulation.Common; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - public partial class GBHawk : IEmulator, IStatable, ISettable - { - public GBSettings GetSettings() - { - return _settings.Clone(); - } - - public GBSyncSettings GetSyncSettings() - { - return _syncSettings.Clone(); - } - - public bool PutSettings(GBSettings o) - { - _settings = o; - return false; - } - - public bool PutSyncSettings(GBSyncSettings o) - { - bool ret = GBSyncSettings.NeedsReboot(_syncSettings, o); - _syncSettings = o; - return ret; - } - - private GBSettings _settings = new GBSettings(); - public GBSyncSettings _syncSettings = new GBSyncSettings(); - - public class GBSettings - { - public GBSettings Clone() - { - return (GBSettings)MemberwiseClone(); - } - } - - public class GBSyncSettings - { - private string _port1 = GBHawkControllerDeck.DefaultControllerName; - - [JsonIgnore] - public string Port1 - { - get { return _port1; } - set - { - if (!GBHawkControllerDeck.ValidControllerTypes.ContainsKey(value)) - { - throw new InvalidOperationException("Invalid controller type: " + value); - } - - _port1 = value; - } - } - - public GBSyncSettings Clone() - { - return (GBSyncSettings)MemberwiseClone(); - } - - public static bool NeedsReboot(GBSyncSettings x, GBSyncSettings y) - { - return !DeepEquality.DeepEquals(x, y); - } - } - } -} diff --git a/GBHawk.IStatable.cs b/GBHawk.IStatable.cs deleted file mode 100644 index a50da0305a..0000000000 --- a/GBHawk.IStatable.cs +++ /dev/null @@ -1,102 +0,0 @@ -using System.IO; - -using BizHawk.Common; -using BizHawk.Emulation.Common; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - public partial class GBHawk : IStatable - { - public bool BinarySaveStatesPreferred => true; - - public void SaveStateText(TextWriter writer) - { - SyncState(new Serializer(writer)); - } - - public void LoadStateText(TextReader reader) - { - SyncState(new Serializer(reader)); - } - - public void SaveStateBinary(BinaryWriter bw) - { - SyncState(new Serializer(bw)); - } - - public void LoadStateBinary(BinaryReader br) - { - SyncState(new Serializer(br)); - } - - public byte[] SaveStateBinary() - { - MemoryStream ms = new MemoryStream(); - BinaryWriter bw = new BinaryWriter(ms); - SaveStateBinary(bw); - bw.Flush(); - return ms.ToArray(); - } - - private void SyncState(Serializer ser) - { - byte[] core = null; - if (ser.IsWriter) - { - var ms = new MemoryStream(); - ms.Close(); - core = ms.ToArray(); - } - cpu.SyncState(ser); - mapper.SyncState(ser); - timer.SyncState(ser); - ppu.SyncState(ser); - audio.SyncState(ser); - - ser.BeginSection("Gameboy"); - ser.Sync("core", ref core, false); - ser.Sync("Lag", ref _lagcount); - ser.Sync("Frame", ref _frame); - ser.Sync("IsLag", ref _islag); - _controllerDeck.SyncState(ser); - - ser.Sync("controller_state", ref controller_state); - ser.Sync("controller_state_old", ref controller_state_old); - ser.Sync("in_vblank", ref in_vblank); - ser.Sync("in_vblank_old", ref in_vblank_old); - ser.Sync("vblank_rise", ref vblank_rise); - ser.Sync("GB_bios_register", ref GB_bios_register); - ser.Sync("input_register", ref input_register); - - ser.Sync("serial_control", ref serial_control); - ser.Sync("serial_data_out", ref serial_data_out); - ser.Sync("serial_data_in", ref serial_data_in); - ser.Sync("serial_start_old", ref serial_start_old); - - ser.Sync("REG_FFFF", ref REG_FFFF); - ser.Sync("REG_FF0F", ref REG_FF0F); - ser.Sync("enable_VBL", ref enable_VBL); - ser.Sync("enable_LCDC", ref enable_PRS); - ser.Sync("enable_TIMO", ref enable_TIMO); - ser.Sync("enable_SER", ref enable_SER); - ser.Sync("enable_STAT", ref enable_STAT); - - // memory domains - ser.Sync("RAM", ref RAM, false); - ser.Sync("ZP_RAM", ref ZP_RAM, false); - ser.Sync("CHR_RAM", ref CHR_RAM, false); - ser.Sync("BG_map_1", ref BG_map_1, false); - ser.Sync("BG_map_2", ref BG_map_2, false); - ser.Sync("OAM", ref OAM, false); - // probably a better way to do this - if (cart_RAM != null) - { - ser.Sync("cart_RAM", ref cart_RAM, false); - } - - - - ser.EndSection(); - } - } -} diff --git a/GBHawk.cs b/GBHawk.cs deleted file mode 100644 index 8a4ff534bf..0000000000 --- a/GBHawk.cs +++ /dev/null @@ -1,223 +0,0 @@ -using System; - -using BizHawk.Common.BufferExtensions; -using BizHawk.Emulation.Common; -using BizHawk.Emulation.Common.Components.LR35902; -using BizHawk.Common.NumberExtensions; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - [Core( - "GBHawk", - "", - isPorted: false, - isReleased: true)] - [ServiceNotApplicable(typeof(ISettable<,>), typeof(IDriveLight))] - public partial class GBHawk : IEmulator, ISaveRam, IDebuggable, IStatable, IInputPollable, IRegionable, - ISettable - { - // this register controls whether or not the GB BIOS is mapped into memory - public byte GB_bios_register; - - public byte input_register; - - public byte serial_control; - public byte serial_data_out; - public byte serial_data_in; - public bool serial_start_old; - - // The unused bits in this register are still read/writable - public byte REG_FFFF; - // The unused bits in this register (interrupt flags) are always set - public byte REG_FF0F = 0xE0; - public bool enable_VBL; - public bool enable_STAT; - public bool enable_TIMO; - public bool enable_SER; - public bool enable_PRS; - - - // memory domains - public byte[] RAM = new byte[0x2000]; - public byte[] ZP_RAM = new byte[0x80]; - public byte[] CHR_RAM = new byte[0x1800]; - public byte[] BG_map_1 = new byte[0x400]; - public byte[] BG_map_2 = new byte[0x400]; - public byte[] OAM = new byte[0xA0]; - - public readonly byte[] _rom; - public readonly byte[] _bios; - public readonly byte[] _sram = new byte[2048]; - public readonly byte[] header = new byte[0x50]; - - public byte[] cart_RAM; - - private int _frame = 0; - - public MapperBase mapper; - - private readonly ITraceable _tracer; - - public LR35902 cpu; - public PPU ppu; - public Timer timer; - public Audio audio; - - [CoreConstructor("GB")] - public GBHawk(CoreComm comm, GameInfo game, byte[] rom, /*string gameDbFn,*/ object settings, object syncSettings) - { - var ser = new BasicServiceProvider(this); - - cpu = new LR35902 - { - ReadMemory = ReadMemory, - WriteMemory = WriteMemory, - PeekMemory = ReadMemory, - DummyReadMemory = ReadMemory, - OnExecFetch = ExecFetch - }; - ppu = new PPU(); - timer = new Timer(); - audio = new Audio(); - - CoreComm = comm; - - _settings = (GBSettings)settings ?? new GBSettings(); - _syncSettings = (GBSyncSettings)syncSettings ?? new GBSyncSettings(); - _controllerDeck = new GBHawkControllerDeck(_syncSettings.Port1); - - byte[] Bios = comm.CoreFileProvider.GetFirmware("GB", "World", false, "BIOS Not Found, Cannot Load"); - _bios = Bios; - - Buffer.BlockCopy(rom, 0x100, header, 0, 0x50); - - string hash_md5 = null; - hash_md5 = "md5:" + rom.HashMD5(0, rom.Length); - Console.WriteLine(hash_md5); - - _rom = rom; - Setup_Mapper(); - - _frameHz = 60; - - timer.Core = this; - audio.Core = this; - ppu.Core = this; - - ser.Register(this); - ser.Register(audio); - ServiceProvider = ser; - - _tracer = new TraceBuffer { Header = cpu.TraceHeader }; - ser.Register(_tracer); - - SetupMemoryDomains(); - HardReset(); - } - - public DisplayType Region => DisplayType.NTSC; - - private readonly GBHawkControllerDeck _controllerDeck; - - private void HardReset() - { - GB_bios_register = 0; // bios enable - in_vblank = true; // we start off in vblank since the LCD is off - in_vblank_old = true; - - Register_Reset(); - timer.Reset(); - ppu.Reset(); - - cpu.SetCallbacks(ReadMemory, ReadMemory, ReadMemory, WriteMemory); - - _vidbuffer = new int[VirtualWidth * VirtualHeight]; - } - - private void ExecFetch(ushort addr) - { - MemoryCallbacks.CallExecutes(addr); - } - - private void Setup_Mapper() - { - // setup up mapper based on header entry - switch (header[0x47]) - { - case 0x0: mapper = new MapperDefault(); break; - case 0x1: mapper = new MapperMBC1(); break; - case 0x2: mapper = new MapperMBC1(); break; - case 0x3: mapper = new MapperMBC1(); break; - case 0x5: mapper = new MapperMBC2(); break; - case 0x6: mapper = new MapperMBC2(); break; - case 0x8: mapper = new MapperDefault(); break; - case 0x9: mapper = new MapperDefault(); break; - case 0xB: mapper = new MapperMMM01(); break; - case 0xC: mapper = new MapperMMM01(); break; - case 0xD: mapper = new MapperMMM01(); break; - case 0xF: mapper = new MapperMBC3(); break; - case 0x10: mapper = new MapperMBC3(); break; - case 0x11: mapper = new MapperMBC3(); break; - case 0x12: mapper = new MapperMBC3(); break; - case 0x13: mapper = new MapperMBC3(); break; - case 0x19: mapper = new MapperMBC5(); break; - case 0x1A: mapper = new MapperMBC5(); break; - case 0x1B: mapper = new MapperMBC5(); break; - case 0x1C: mapper = new MapperMBC5(); break; - case 0x1D: mapper = new MapperMBC5(); break; - case 0x1E: mapper = new MapperMBC5(); break; - case 0x20: mapper = new MapperMBC6(); break; - case 0x22: mapper = new MapperMBC7(); break; - case 0xFC: mapper = new MapperCamera(); break; - case 0xFD: mapper = new MapperTAMA5(); break; - case 0xFE: mapper = new MapperHuC3(); break; - case 0xFF: mapper = new MapperHuC1(); break; - - case 0x4: - case 0x7: - case 0xA: - case 0xE: - case 0x14: - case 0x15: - case 0x16: - case 0x17: - case 0x18: - case 0x1F: - case 0x21: - default: - // mapper not implemented - throw new Exception("Mapper not implemented"); - break; - - } - - Console.Write("Mapper: "); - Console.WriteLine(header[0x47]); - - cart_RAM = null; - - switch (header[0x49]) - { - case 1: - cart_RAM = new byte[0x800]; - break; - case 2: - cart_RAM = new byte[0x2000]; - break; - case 3: - cart_RAM = new byte[0x8000]; - break; - case 4: - cart_RAM = new byte[0x20000]; - break; - case 5: - cart_RAM = new byte[0x10000]; - break; - - } - - mapper.Core = this; - mapper.Initialize(); - } - } -} diff --git a/GBHawkControllerDeck.cs b/GBHawkControllerDeck.cs deleted file mode 100644 index 464c4bfdcb..0000000000 --- a/GBHawkControllerDeck.cs +++ /dev/null @@ -1,76 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; - -using BizHawk.Common; -using BizHawk.Common.ReflectionExtensions; -using BizHawk.Emulation.Common; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - public class GBHawkControllerDeck - { - public GBHawkControllerDeck(string controller1Name) - { - if (!ValidControllerTypes.ContainsKey(controller1Name)) - { - throw new InvalidOperationException("Invalid controller type: " + controller1Name); - } - - Port1 = (IPort)Activator.CreateInstance(ValidControllerTypes[controller1Name], 1); - - Definition = new ControllerDefinition - { - Name = Port1.Definition.Name, - BoolButtons = Port1.Definition.BoolButtons - .Concat(new[] - { - "Power", - "Reset", - }) - .ToList() - }; - - Definition.FloatControls.AddRange(Port1.Definition.FloatControls); - - Definition.FloatRanges.AddRange(Port1.Definition.FloatRanges); - } - - public byte ReadPort1(IController c) - { - return Port1.Read(c); - } - - public ControllerDefinition Definition { get; } - - public void SyncState(Serializer ser) - { - ser.BeginSection("Port1"); - Port1.SyncState(ser); - ser.EndSection(); - } - - private readonly IPort Port1; - - private static Dictionary _controllerTypes; - - public static Dictionary ValidControllerTypes - { - get - { - if (_controllerTypes == null) - { - _controllerTypes = typeof(GBHawkControllerDeck).Assembly - .GetTypes() - .Where(t => typeof(IPort).IsAssignableFrom(t)) - .Where(t => !t.IsAbstract && !t.IsInterface) - .ToDictionary(tkey => tkey.DisplayName()); - } - - return _controllerTypes; - } - } - - public static string DefaultControllerName => typeof(StandardControls).DisplayName(); - } -} diff --git a/GBHawkControllers.cs b/GBHawkControllers.cs deleted file mode 100644 index af504834c7..0000000000 --- a/GBHawkControllers.cs +++ /dev/null @@ -1,68 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; - -using BizHawk.Common; -using BizHawk.Emulation.Common; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - /// - /// Represents a GB add on - /// - public interface IPort - { - byte Read(IController c); - - ControllerDefinition Definition { get; } - - void SyncState(Serializer ser); - - int PortNum { get; } - } - - [DisplayName("Standard controls")] - public class StandardControls : IPort - { - public StandardControls(int portNum) - { - PortNum = portNum; - Definition = new ControllerDefinition - { - Name = "Game Boy", - BoolButtons = BaseDefinition - .Select(b => "P" + PortNum + " " + b) - .ToList() - }; - } - - public int PortNum { get; } - - public ControllerDefinition Definition { get; } - - public byte Read(IController c) - { - byte result = 0xFF; - for (int i = 0; i < 8; i++) - { - if (c.IsPressed(Definition.BoolButtons[i])) - { - result -= (byte)(1 << i); - } - } - - return result; - } - - private static readonly string[] BaseDefinition = - { - "Right", "Left", "Up", "Down", "A", "B", "Select", "Start" - }; - - public void SyncState(Serializer ser) - { - //nothing - } - } -} \ No newline at end of file diff --git a/HW_Registers.cs b/HW_Registers.cs deleted file mode 100644 index 3e71185e35..0000000000 --- a/HW_Registers.cs +++ /dev/null @@ -1,283 +0,0 @@ -using System; -using BizHawk.Emulation.Common; -using BizHawk.Common.NumberExtensions; -using BizHawk.Common; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - public partial class GBHawk - { - public byte Read_Registers(int addr) - { - byte ret = 0; - - switch (addr) - { - // Read Input - case 0xFF00: - _islag = false; - - input_register &= 0xF0; - if ((input_register & 0x30) == 0x20) - { - input_register |= (byte)(controller_state & 0xF); - } - else if ((input_register & 0x30) == 0x10) - { - input_register |= (byte)((controller_state & 0xF0) >> 4); - } - else if ((input_register & 0x30) == 0x30) - { - // if both polls are set, then a bit is zero if either or both pins are zero - byte temp = (byte)((controller_state & 0xF) & ((controller_state & 0xF0) >> 4)); - input_register |= temp; - } - else - { - input_register |= 0xF; - } - ret = input_register; - break; - - // Serial data port - case 0xFF01: - ret = serial_data_in; - break; - - // Serial port control - case 0xFF02: - ret = serial_control; - break; - - // Timer Registers - case 0xFF04: - case 0xFF05: - case 0xFF06: - case 0xFF07: - ret = timer.ReadReg(addr); - break; - - // Interrupt flags - case 0xFF0F: - ret = REG_FF0F; - break; - - // audio regs - case 0xFF10: - case 0xFF11: - case 0xFF12: - case 0xFF13: - case 0xFF14: - case 0xFF16: - case 0xFF17: - case 0xFF18: - case 0xFF19: - case 0xFF1A: - case 0xFF1B: - case 0xFF1C: - case 0xFF1D: - case 0xFF1E: - case 0xFF20: - case 0xFF21: - case 0xFF22: - case 0xFF23: - case 0xFF24: - case 0xFF25: - case 0xFF26: - case 0xFF30: - case 0xFF31: - case 0xFF32: - case 0xFF33: - case 0xFF34: - case 0xFF35: - case 0xFF36: - case 0xFF37: - case 0xFF38: - case 0xFF39: - case 0xFF3A: - case 0xFF3B: - case 0xFF3C: - case 0xFF3D: - case 0xFF3E: - case 0xFF3F: - ret = audio.ReadReg(addr); - break; - - // PPU Regs - case 0xFF40: - case 0xFF41: - case 0xFF42: - case 0xFF43: - case 0xFF44: - case 0xFF45: - case 0xFF46: - case 0xFF47: - case 0xFF48: - case 0xFF49: - case 0xFF4A: - case 0xFF4B: - ret = ppu.ReadReg(addr); - break; - - // Bios control register. Not sure if it is readable - case 0xFF50: - ret = 0xFF; - break; - - // interrupt control register - case 0xFFFF: - ret = REG_FFFF; - break; - - default: - ret = 0xFF; - break; - - } - return ret; - } - - public void Write_Registers(int addr, byte value) - { - switch (addr) - { - // select input - case 0xFF00: - input_register = (byte)(0xC0 | (value & 0x3F)); // top 2 bits always 1 - break; - - // Serial data port - case 0xFF01: - serial_data_out = value; - serial_data_in = serial_data_out; - break; - - // Serial port control - case 0xFF02: - serial_control = (byte)(0x7E | (value & 0x81)); // middle six bits always 1 - break; - - // Timer Registers - case 0xFF04: - case 0xFF05: - case 0xFF06: - case 0xFF07: - timer.WriteReg(addr, value); - break; - - // Interrupt flags - case 0xFF0F: - REG_FF0F = (byte)(0xE0 | value); - - // check if enabling any of the bits triggered an IRQ - for (int i = 0; i < 5; i++) - { - if (REG_FFFF.Bit(i) && REG_FF0F.Bit(i)) - { - cpu.FlagI = true; - } - } - - // if no bits are in common between flags and enables, de-assert the IRQ - if (((REG_FF0F & 0x1F) & REG_FFFF) == 0) { cpu.FlagI = false; } - - break; - - // audio regs - case 0xFF10: - case 0xFF11: - case 0xFF12: - case 0xFF13: - case 0xFF14: - case 0xFF16: - case 0xFF17: - case 0xFF18: - case 0xFF19: - case 0xFF1A: - case 0xFF1B: - case 0xFF1C: - case 0xFF1D: - case 0xFF1E: - case 0xFF20: - case 0xFF21: - case 0xFF22: - case 0xFF23: - case 0xFF24: - case 0xFF25: - case 0xFF26: - case 0xFF30: - case 0xFF31: - case 0xFF32: - case 0xFF33: - case 0xFF34: - case 0xFF35: - case 0xFF36: - case 0xFF37: - case 0xFF38: - case 0xFF39: - case 0xFF3A: - case 0xFF3B: - case 0xFF3C: - case 0xFF3D: - case 0xFF3E: - case 0xFF3F: - audio.WriteReg(addr, value); - break; - - // PPU Regs - case 0xFF40: - case 0xFF41: - case 0xFF42: - case 0xFF43: - case 0xFF44: - case 0xFF45: - case 0xFF46: - case 0xFF47: - case 0xFF48: - case 0xFF49: - case 0xFF4A: - case 0xFF4B: - ppu.WriteReg(addr, value); - break; - - // Bios control register. Writing 1 permanently disables BIOS until a power cycle occurs - case 0xFF50: - //Console.WriteLine(value); - if (GB_bios_register != 1) - { - GB_bios_register = value; - } - break; - - // interrupt control register - case 0xFFFF: - REG_FFFF = value; - enable_VBL = REG_FFFF.Bit(0); - enable_STAT = REG_FFFF.Bit(1); - enable_TIMO = REG_FFFF.Bit(2); - enable_SER = REG_FFFF.Bit(3); - enable_PRS = REG_FFFF.Bit(4); - - // check if enabling any of the bits triggered an IRQ - for (int i = 0; i < 5; i++) - { - if (REG_FFFF.Bit(i) && REG_FF0F.Bit(i)) - { - cpu.FlagI = true; - } - } - - // if no bits are in common between flags and enables, de-assert the IRQ - if (((REG_FF0F & 0x1F) & REG_FFFF) == 0) { cpu.FlagI = false; } - - break; - } - } - - public void Register_Reset() - { - input_register = 0xCF; // not reading any input - serial_control = 0x7E; - } - } -} diff --git a/Mappers/MapperBase.cs b/Mappers/MapperBase.cs deleted file mode 100644 index f7aeb7ddca..0000000000 --- a/Mappers/MapperBase.cs +++ /dev/null @@ -1,40 +0,0 @@ -using BizHawk.Common; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - public class MapperBase - { - public GBHawk Core { get; set; } - - public virtual byte ReadMemory(ushort addr) - { - return 0; - } - - public virtual byte PeekMemory(ushort addr) - { - return 0; - } - - public virtual void WriteMemory(ushort addr, byte value) - { - } - - public virtual void PokeMemory(ushort addr, byte value) - { - } - - public virtual void SyncState(Serializer ser) - { - } - - public virtual void Dispose() - { - } - - public virtual void Initialize() - { - } - } -} diff --git a/Mappers/Mapper_Camera.cs b/Mappers/Mapper_Camera.cs deleted file mode 100644 index e247725259..0000000000 --- a/Mappers/Mapper_Camera.cs +++ /dev/null @@ -1,59 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Default mapper with no bank switching - public class MapperCamera : MapperBase - { - public override void Initialize() - { - // nothing to initialize - } - - public override byte ReadMemory(ushort addr) - { - if (addr < 0x8000) - { - return Core._rom[addr]; - } - else - { - if (Core.cart_RAM != null) - { - return Core.cart_RAM[addr - 0xA000]; - } - else - { - return 0; - } - } - } - - public override byte PeekMemory(ushort addr) - { - return ReadMemory(addr); - } - - public override void WriteMemory(ushort addr, byte value) - { - if (addr < 0x8000) - { - // no mapping hardware available - } - else - { - if (Core.cart_RAM != null) - { - Core.cart_RAM[addr - 0xA000] = value; - } - } - } - - public override void PokeMemory(ushort addr, byte value) - { - WriteMemory(addr, value); - } - } -} diff --git a/Mappers/Mapper_Default.cs b/Mappers/Mapper_Default.cs deleted file mode 100644 index 609a696040..0000000000 --- a/Mappers/Mapper_Default.cs +++ /dev/null @@ -1,59 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Default mapper with no bank switching - public class MapperDefault : MapperBase - { - public override void Initialize() - { - // nothing to initialize - } - - public override byte ReadMemory(ushort addr) - { - if (addr < 0x8000) - { - return Core._rom[addr]; - } - else - { - if (Core.cart_RAM != null) - { - return Core.cart_RAM[addr - 0xA000]; - } - else - { - return 0; - } - } - } - - public override byte PeekMemory(ushort addr) - { - return ReadMemory(addr); - } - - public override void WriteMemory(ushort addr, byte value) - { - if (addr < 0x8000) - { - // no mapping hardware available - } - else - { - if (Core.cart_RAM != null) - { - Core.cart_RAM[addr - 0xA000] = value; - } - } - } - - public override void PokeMemory(ushort addr, byte value) - { - WriteMemory(addr, value); - } - } -} diff --git a/Mappers/Mapper_HuC1.cs b/Mappers/Mapper_HuC1.cs deleted file mode 100644 index 0e33db1474..0000000000 --- a/Mappers/Mapper_HuC1.cs +++ /dev/null @@ -1,59 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Default mapper with no bank switching - public class MapperHuC1 : MapperBase - { - public override void Initialize() - { - // nothing to initialize - } - - public override byte ReadMemory(ushort addr) - { - if (addr < 0x8000) - { - return Core._rom[addr]; - } - else - { - if (Core.cart_RAM != null) - { - return Core.cart_RAM[addr - 0xA000]; - } - else - { - return 0; - } - } - } - - public override byte PeekMemory(ushort addr) - { - return ReadMemory(addr); - } - - public override void WriteMemory(ushort addr, byte value) - { - if (addr < 0x8000) - { - // no mapping hardware available - } - else - { - if (Core.cart_RAM != null) - { - Core.cart_RAM[addr - 0xA000] = value; - } - } - } - - public override void PokeMemory(ushort addr, byte value) - { - WriteMemory(addr, value); - } - } -} diff --git a/Mappers/Mapper_HuC3.cs b/Mappers/Mapper_HuC3.cs deleted file mode 100644 index ff0e5cc6d1..0000000000 --- a/Mappers/Mapper_HuC3.cs +++ /dev/null @@ -1,59 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Default mapper with no bank switching - public class MapperHuC3 : MapperBase - { - public override void Initialize() - { - // nothing to initialize - } - - public override byte ReadMemory(ushort addr) - { - if (addr < 0x8000) - { - return Core._rom[addr]; - } - else - { - if (Core.cart_RAM != null) - { - return Core.cart_RAM[addr - 0xA000]; - } - else - { - return 0; - } - } - } - - public override byte PeekMemory(ushort addr) - { - return ReadMemory(addr); - } - - public override void WriteMemory(ushort addr, byte value) - { - if (addr < 0x8000) - { - // no mapping hardware available - } - else - { - if (Core.cart_RAM != null) - { - Core.cart_RAM[addr - 0xA000] = value; - } - } - } - - public override void PokeMemory(ushort addr, byte value) - { - WriteMemory(addr, value); - } - } -} diff --git a/Mappers/Mapper_MBC1.cs b/Mappers/Mapper_MBC1.cs deleted file mode 100644 index 2a8bed26be..0000000000 --- a/Mappers/Mapper_MBC1.cs +++ /dev/null @@ -1,130 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // MBC1 with bank switching and RAM - public class MapperMBC1 : MapperBase - { - public int ROM_bank; - public int RAM_bank; - public bool RAM_enable; - public bool sel_mode; - - public override void Initialize() - { - ROM_bank = 1; - RAM_bank = 0; - RAM_enable = false; - sel_mode = false; - } - - public override byte ReadMemory(ushort addr) - { - if (addr < 0x4000) - { - // lowest bank is fixed - return Core._rom[addr]; - } - else if (addr < 0x8000) - { - return Core._rom[(addr - 0x4000) + ROM_bank * 0x4000]; - } - else - { - if (Core.cart_RAM != null) - { - if (RAM_enable) - { - return Core.cart_RAM[(addr - 0xA000) + RAM_bank * 0x2000]; - } - else - { - return 0; - } - - } - else - { - return 0; - } - } - } - - public override byte PeekMemory(ushort addr) - { - return ReadMemory(addr); - } - - public override void WriteMemory(ushort addr, byte value) - { - if (addr < 0x8000) - { - if (addr < 0x2000) - { - RAM_enable = ((value & 0xA) == 0xA) ? true : false; - } - else if (addr < 0x4000) - { - value &= 0x1F; - - // writing zero gets translated to 1 - if (value == 0) { value = 1; } - - ROM_bank &= 0xE0; - ROM_bank |= value; - } - else if (addr < 0x6000) - { - if (sel_mode) - { - RAM_bank = value & 0x3; - } - else - { - ROM_bank &= 0x1F; - ROM_bank |= ((value & 3) << 5); - } - } - else - { - sel_mode = (value & 1) > 0; - - if (sel_mode) - { - ROM_bank &= 0x1F; - } - else - { - RAM_bank = 0; - } - } - } - else - { - if (Core.cart_RAM != null) - { - if (RAM_enable) - { - Core.cart_RAM[(addr - 0xA000) + RAM_bank * 0x2000] = value; - } - - } - } - } - - public override void PokeMemory(ushort addr, byte value) - { - WriteMemory(addr, value); - } - - public override void SyncState(Serializer ser) - { - ser.Sync("ROM_Bank", ref ROM_bank); - ser.Sync("RAM_Bank", ref RAM_bank); - ser.Sync("RAM_enable", ref RAM_enable); - ser.Sync("sel_mode", ref sel_mode); - } - } -} diff --git a/Mappers/Mapper_MBC2.cs b/Mappers/Mapper_MBC2.cs deleted file mode 100644 index 3130aaa469..0000000000 --- a/Mappers/Mapper_MBC2.cs +++ /dev/null @@ -1,59 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Default mapper with no bank switching - public class MapperMBC2 : MapperBase - { - public override void Initialize() - { - // nothing to initialize - } - - public override byte ReadMemory(ushort addr) - { - if (addr < 0x8000) - { - return Core._rom[addr]; - } - else - { - if (Core.cart_RAM != null) - { - return Core.cart_RAM[addr - 0xA000]; - } - else - { - return 0; - } - } - } - - public override byte PeekMemory(ushort addr) - { - return ReadMemory(addr); - } - - public override void WriteMemory(ushort addr, byte value) - { - if (addr < 0x8000) - { - // no mapping hardware available - } - else - { - if (Core.cart_RAM != null) - { - Core.cart_RAM[addr - 0xA000] = value; - } - } - } - - public override void PokeMemory(ushort addr, byte value) - { - WriteMemory(addr, value); - } - } -} diff --git a/Mappers/Mapper_MBC3.cs b/Mappers/Mapper_MBC3.cs deleted file mode 100644 index 961f1769e4..0000000000 --- a/Mappers/Mapper_MBC3.cs +++ /dev/null @@ -1,59 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Default mapper with no bank switching - public class MapperMBC3 : MapperBase - { - public override void Initialize() - { - // nothing to initialize - } - - public override byte ReadMemory(ushort addr) - { - if (addr < 0x8000) - { - return Core._rom[addr]; - } - else - { - if (Core.cart_RAM != null) - { - return Core.cart_RAM[addr - 0xA000]; - } - else - { - return 0; - } - } - } - - public override byte PeekMemory(ushort addr) - { - return ReadMemory(addr); - } - - public override void WriteMemory(ushort addr, byte value) - { - if (addr < 0x8000) - { - // no mapping hardware available - } - else - { - if (Core.cart_RAM != null) - { - Core.cart_RAM[addr - 0xA000] = value; - } - } - } - - public override void PokeMemory(ushort addr, byte value) - { - WriteMemory(addr, value); - } - } -} diff --git a/Mappers/Mapper_MBC5.cs b/Mappers/Mapper_MBC5.cs deleted file mode 100644 index 312c9dc108..0000000000 --- a/Mappers/Mapper_MBC5.cs +++ /dev/null @@ -1,59 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Default mapper with no bank switching - public class MapperMBC5 : MapperBase - { - public override void Initialize() - { - // nothing to initialize - } - - public override byte ReadMemory(ushort addr) - { - if (addr < 0x8000) - { - return Core._rom[addr]; - } - else - { - if (Core.cart_RAM != null) - { - return Core.cart_RAM[addr - 0xA000]; - } - else - { - return 0; - } - } - } - - public override byte PeekMemory(ushort addr) - { - return ReadMemory(addr); - } - - public override void WriteMemory(ushort addr, byte value) - { - if (addr < 0x8000) - { - // no mapping hardware available - } - else - { - if (Core.cart_RAM != null) - { - Core.cart_RAM[addr - 0xA000] = value; - } - } - } - - public override void PokeMemory(ushort addr, byte value) - { - WriteMemory(addr, value); - } - } -} diff --git a/Mappers/Mapper_MBC6.cs b/Mappers/Mapper_MBC6.cs deleted file mode 100644 index 7f9624adb9..0000000000 --- a/Mappers/Mapper_MBC6.cs +++ /dev/null @@ -1,59 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Default mapper with no bank switching - public class MapperMBC6 : MapperBase - { - public override void Initialize() - { - // nothing to initialize - } - - public override byte ReadMemory(ushort addr) - { - if (addr < 0x8000) - { - return Core._rom[addr]; - } - else - { - if (Core.cart_RAM != null) - { - return Core.cart_RAM[addr - 0xA000]; - } - else - { - return 0; - } - } - } - - public override byte PeekMemory(ushort addr) - { - return ReadMemory(addr); - } - - public override void WriteMemory(ushort addr, byte value) - { - if (addr < 0x8000) - { - // no mapping hardware available - } - else - { - if (Core.cart_RAM != null) - { - Core.cart_RAM[addr - 0xA000] = value; - } - } - } - - public override void PokeMemory(ushort addr, byte value) - { - WriteMemory(addr, value); - } - } -} diff --git a/Mappers/Mapper_MBC7.cs b/Mappers/Mapper_MBC7.cs deleted file mode 100644 index 40c9513b8b..0000000000 --- a/Mappers/Mapper_MBC7.cs +++ /dev/null @@ -1,59 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Default mapper with no bank switching - public class MapperMBC7 : MapperBase - { - public override void Initialize() - { - // nothing to initialize - } - - public override byte ReadMemory(ushort addr) - { - if (addr < 0x8000) - { - return Core._rom[addr]; - } - else - { - if (Core.cart_RAM != null) - { - return Core.cart_RAM[addr - 0xA000]; - } - else - { - return 0; - } - } - } - - public override byte PeekMemory(ushort addr) - { - return ReadMemory(addr); - } - - public override void WriteMemory(ushort addr, byte value) - { - if (addr < 0x8000) - { - // no mapping hardware available - } - else - { - if (Core.cart_RAM != null) - { - Core.cart_RAM[addr - 0xA000] = value; - } - } - } - - public override void PokeMemory(ushort addr, byte value) - { - WriteMemory(addr, value); - } - } -} diff --git a/Mappers/Mapper_MMM01.cs b/Mappers/Mapper_MMM01.cs deleted file mode 100644 index 86c07e20ca..0000000000 --- a/Mappers/Mapper_MMM01.cs +++ /dev/null @@ -1,59 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Default mapper with no bank switching - public class MapperMMM01 : MapperBase - { - public override void Initialize() - { - // nothing to initialize - } - - public override byte ReadMemory(ushort addr) - { - if (addr < 0x8000) - { - return Core._rom[addr]; - } - else - { - if (Core.cart_RAM != null) - { - return Core.cart_RAM[addr - 0xA000]; - } - else - { - return 0; - } - } - } - - public override byte PeekMemory(ushort addr) - { - return ReadMemory(addr); - } - - public override void WriteMemory(ushort addr, byte value) - { - if (addr < 0x8000) - { - // no mapping hardware available - } - else - { - if (Core.cart_RAM != null) - { - Core.cart_RAM[addr - 0xA000] = value; - } - } - } - - public override void PokeMemory(ushort addr, byte value) - { - WriteMemory(addr, value); - } - } -} diff --git a/Mappers/Mapper_TAMA5.cs b/Mappers/Mapper_TAMA5.cs deleted file mode 100644 index eed5909336..0000000000 --- a/Mappers/Mapper_TAMA5.cs +++ /dev/null @@ -1,59 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Default mapper with no bank switching - public class MapperTAMA5 : MapperBase - { - public override void Initialize() - { - // nothing to initialize - } - - public override byte ReadMemory(ushort addr) - { - if (addr < 0x8000) - { - return Core._rom[addr]; - } - else - { - if (Core.cart_RAM != null) - { - return Core.cart_RAM[addr - 0xA000]; - } - else - { - return 0; - } - } - } - - public override byte PeekMemory(ushort addr) - { - return ReadMemory(addr); - } - - public override void WriteMemory(ushort addr, byte value) - { - if (addr < 0x8000) - { - // no mapping hardware available - } - else - { - if (Core.cart_RAM != null) - { - Core.cart_RAM[addr - 0xA000] = value; - } - } - } - - public override void PokeMemory(ushort addr, byte value) - { - WriteMemory(addr, value); - } - } -} diff --git a/Mappers/ReadMe.txt b/Mappers/ReadMe.txt deleted file mode 100644 index 0c94c8272c..0000000000 --- a/Mappers/ReadMe.txt +++ /dev/null @@ -1,3 +0,0 @@ -TODO: -Official Mappers -Unofficial Mappers diff --git a/MemoryMap.cs b/MemoryMap.cs deleted file mode 100644 index 8357ebe073..0000000000 --- a/MemoryMap.cs +++ /dev/null @@ -1,164 +0,0 @@ -using System; - -using BizHawk.Common.BufferExtensions; -using BizHawk.Emulation.Common; - - -/* - $FFFF Interrupt Enable Flag - $FF80-$FFFE Zero Page - 127 bytes - $FF00-$FF7F Hardware I/O Registers - $FEA0-$FEFF Unusable Memory - $FE00-$FE9F OAM - Object Attribute Memory - $E000-$FDFF Echo RAM - Reserved, Do Not Use - $D000-$DFFF Internal RAM - Bank 1-7 (switchable - CGB only) - $C000-$CFFF Internal RAM - Bank 0 (fixed) - $A000-$BFFF Cartridge RAM (If Available) - $9C00-$9FFF BG Map Data 2 - $9800-$9BFF BG Map Data 1 - $8000-$97FF Character RAM - $4000-$7FFF Cartridge ROM - Switchable Banks 1-xx - $0150-$3FFF Cartridge ROM - Bank 0 (fixed) - $0100-$014F Cartridge Header Area - $0000-$00FF Restart and Interrupt Vectors -*/ - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - public partial class GBHawk - { - public byte ReadMemory(ushort addr) - { - MemoryCallbacks.CallReads(addr); - - if (addr < 0x100) - { - // return Either BIOS ROM or Game ROM - if ((GB_bios_register & 0x1) == 0) - { - return _bios[addr]; // Return BIOS - } - else - { - return mapper.ReadMemory(addr); - } - } - else if (addr < 0x8000) - { - return mapper.ReadMemory(addr); - } - else if (addr < 0x9800) - { - return CHR_RAM[addr - 0x8000]; - } - else if (addr < 0x9C00) - { - return BG_map_1[addr - 0x9800]; - } - else if (addr < 0xA000) - { - return BG_map_2[addr - 0x9C00]; - } - else if (addr < 0xC000) - { - return mapper.ReadMemory(addr); - } - else if (addr < 0xE000) - { - return RAM[addr - 0xC000]; - } - else if (addr < 0xFE00) - { - return RAM[addr - 0xE000]; - } - else if (addr < 0xFEA0 && ppu.OAM_access) - { - return OAM[addr - 0xFE00]; - } - else if (addr < 0xFF00) - { - // unmapped memory, returns 0xFF - return 0xFF; - } - else if (addr < 0xFF80) - { - return Read_Registers(addr); - } - else if (addr < 0xFFFF) - { - return ZP_RAM[addr - 0xFF80]; - } - else - { - return Read_Registers(addr); - } - - } - - public void WriteMemory(ushort addr, byte value) - { - MemoryCallbacks.CallWrites(addr); - - if (addr < 0x100) - { - // return Either BIOS ROM or Game ROM - if ((GB_bios_register & 0x1) == 0) - { - // Can't write to BIOS region - } - else - { - mapper.WriteMemory(addr, value); - } - } - else if (addr < 0x8000) - { - mapper.WriteMemory(addr, value); - } - else if (addr < 0x9800) - { - CHR_RAM[addr - 0x8000] = value; - } - else if (addr < 0x9C00) - { - BG_map_1[addr - 0x9800] = value; - } - else if (addr < 0xA000) - { - BG_map_2[addr - 0x9C00] = value; - } - else if (addr < 0xC000) - { - mapper.WriteMemory(addr, value); - } - else if (addr < 0xE000) - { - RAM[addr - 0xC000] = value; - } - else if (addr < 0xFE00) - { - RAM[addr - 0xE000] = value; - } - else if (addr < 0xFEA0 && ppu.OAM_access) - { - OAM[addr - 0xFE00] = value; - } - else if (addr < 0xFF00) - { - // unmapped, writing has no effect - } - else if (addr < 0xFF80) - { - Write_Registers(addr, value); - } - else if (addr < 0xFFFF) - { - ZP_RAM[addr - 0xFF80] = value; - } - else - { - Write_Registers(addr, value); - } - } - } -} diff --git a/PPU.cs b/PPU.cs deleted file mode 100644 index 9170cf1128..0000000000 --- a/PPU.cs +++ /dev/null @@ -1,922 +0,0 @@ -using System; -using BizHawk.Emulation.Common; -using BizHawk.Common.NumberExtensions; -using BizHawk.Common; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - public class PPU - { - public GBHawk Core { get; set; } - - //public byte BGP_l; - - // register variables - public byte LCDC; - public byte STAT; - public byte scroll_y; - public byte scroll_x; - public byte LY; - public byte LY_inc; - public byte LYC; - public byte DMA_addr; - public byte BGP; - public byte obj_pal_0; - public byte obj_pal_1; - public byte window_y; - public byte window_x; - public bool DMA_start; - public int DMA_clock; - public int DMA_inc; - public byte DMA_byte; - - // state variables - public int cycle; - public bool LYC_INT; - public bool HBL_INT; - public bool VBL_INT; - public bool OAM_INT; - public bool LCD_was_off; - public bool stat_line; - public bool stat_line_old; - public bool hbl_set_once; - // OAM scan - public bool OAM_access; - public int OAM_scan_index; - public int SL_sprites_index; - public int[] SL_sprites = new int[40]; - public int write_sprite; - // render - public bool VRAM_access; - public int read_case; - public int internal_cycle; - public int y_tile; - public int y_scroll_offset; - public int x_tile; - public int x_scroll_offset; - public int tile_byte; - public int sprite_fetch_cycles; - public bool fetch_sprite; - public int temp_fetch; - public int tile_inc; - public bool pre_render; - public byte[] tile_data = new byte[2]; - public byte[] tile_data_latch = new byte[2]; - public int latch_counter; - public bool latch_new_data; - public int render_counter; - public int render_offset; - public int pixel_counter; - public int pixel; - public byte[] sprite_data = new byte[2]; - public byte[] sprite_sel = new byte[2]; - public int sl_use_index; - public bool no_sprites; - public int sprite_fetch_index; - public int[] SL_sprites_ordered = new int[40]; // (x_end, data_low, data_high, attr) - public int index_used; - public int sprite_ordered_index; - public int bottom_index; - - public byte ReadReg(int addr) - { - byte ret = 0; - - switch (addr) - { - case 0xFF40: ret = LCDC; break; // LCDC - case 0xFF41: ret = STAT; break; // STAT - case 0xFF42: ret = scroll_y; break; // SCY - case 0xFF43: ret = scroll_x; break; // SCX - case 0xFF44: ret = LY; break; // LY - case 0xFF45: ret = LYC; break; // LYC - case 0xFF46: /*ret = DMA_addr; */ break; // DMA (not readable?) - case 0xFF47: ret = BGP; break; // BGP - case 0xFF48: ret = obj_pal_0; break; // OBP0 - case 0xFF49: ret = obj_pal_1; break; // OBP1 - case 0xFF4A: ret = window_y; break; // WY - case 0xFF4B: ret = window_x; break; // WX - } - - return ret; - } - - public void WriteReg(int addr, byte value) - { - switch (addr) - { - case 0xFF40: // LCDC - LCDC = value; - break; - case 0xFF41: // STAT - STAT = (byte)((value & 0xF8) | (STAT & 7) | 0x80); - break; - case 0xFF42: // SCY - scroll_y = value; - break; - case 0xFF43: // SCX - scroll_x = value; - // calculate the column number of the tile to start with - x_tile = (int)Math.Floor((float)(scroll_x) / 8); - break; - case 0xFF44: // LY - LY = 0; /*reset*/ - break; - case 0xFF45: // LYC - LYC = value; - if (LY != LYC) { STAT &= 0xFB; } - break; - case 0xFF46: // DMA - DMA_addr = value; - DMA_start = true; - DMA_clock = 0; - DMA_inc = 0; - break; - case 0xFF47: // BGP - BGP = value; - break; - case 0xFF48: // OBP0 - obj_pal_0 = value; - break; - case 0xFF49: // OBP1 - obj_pal_1 = value; - break; - case 0xFF4A: // WY - window_y = value; - break; - case 0xFF4B: // WX - window_x = value; - break; - } - } - - public void tick() - { - // tick DMA - if (DMA_start) - { - if (DMA_clock >= 4) - { - OAM_access = false; - if ((DMA_clock % 4) == 1) - { - // the cpu can't access memory during this time, but we still need the ppu to be able to. - DMA_start = false; - DMA_byte = Core.ReadMemory((ushort)((DMA_addr << 8) + DMA_inc)); - DMA_start = true; - } - else if ((DMA_clock % 4) == 3) - { - if ((DMA_inc % 4) == 3) - { - Core.OAM[DMA_inc] = DMA_byte; - } - else - { - Core.OAM[DMA_inc] = DMA_byte; - } - - if (DMA_inc < (0xA0 - 1)) { DMA_inc++; } - } - } - - DMA_clock++; - - if (DMA_clock==648) - { - DMA_start = false; - OAM_access = true; - } - } - - // the ppu only does anything if it is turned on via bit 7 of LCDC - if (LCDC.Bit(7)) - { - // exit vblank if LCD went from off to on - if (LCD_was_off) - { - //VBL_INT = false; - Core.in_vblank = false; - LCD_was_off = false; - - // we exit vblank into mode 0 for 4 cycles - // but no hblank interrupt, presumably this only happens transitioning from mode 3 to 0 - STAT &= 0xFC; - } - - // the VBL stat is continuously asserted - if ((LY >= 144)) - { - if (STAT.Bit(4)) - { - if ((cycle >= 4) && (LY == 144)) - { - VBL_INT = true; - } - else if (LY > 144) - { - VBL_INT = true; - } - } - - if ((cycle == 4) && (LY == 144)) { - - HBL_INT = false; - - // set STAT mode to 1 (VBlank) and interrupt flag if it is enabled - STAT &= 0xFC; - STAT |= 0x01; - - if (Core.REG_FFFF.Bit(0)) { Core.cpu.FlagI = true; } - Core.REG_FF0F |= 0x01; - } - - if ((LY >= 144) && (cycle == 4)) - { - // a special case of OAM mode 2 IRQ assertion, even though PPU Mode still is 1 - if (STAT.Bit(5)) { OAM_INT = true; } - } - - if ((LY == 153) && (cycle == 8)) - { - LY = 0; - LY_inc = 0; - Core.cpu.LY = LY; - } - } - - if (!Core.in_vblank) - { - if (cycle == 4) - { - // here mode 2 will be set to true and interrupts fired if enabled - STAT &= 0xFC; - STAT |= 0x2; - if (STAT.Bit(5)) { OAM_INT = true; } - - HBL_INT = false; - } - - if (cycle >= 4 && cycle < 84) - { - // here OAM scanning is performed - OAM_scan(cycle - 4); - } - else if (cycle >= 84 && LY < 144) - { - // render the screen and handle hblank - render(cycle - 84); - } - } - - - if ((LY_inc == 0)) - { - if (cycle == 12) - { - LYC_INT = false; - STAT &= 0xFB; - - // Special case of LY = LYC - if (LY == LYC) - { - // set STAT coincidence FLAG and interrupt flag if it is enabled - STAT |= 0x04; - if (STAT.Bit(6)) { LYC_INT = true; } - } - - // also a special case of OAM mode 2 IRQ assertion, even though PPU Mode still is 1 - if (STAT.Bit(5)) { OAM_INT = true; } - } - - if (cycle == 92) { OAM_INT = false; } - } - - // here LY=LYC will be asserted - if ((cycle == 4) && (LY != 0)) - { - LYC_INT = false; - STAT &= 0xFB; - - if (LY == LYC) - { - // set STAT coincidence FLAG and interrupt flag if it is enabled - STAT |= 0x04; - if (STAT.Bit(6)) { LYC_INT = true; } - } - } - - cycle++; - - if (cycle==456) - { - cycle = 0; - LY+=LY_inc; - - if (LY==0 && LY_inc == 0) - { - LY_inc = 1; - Core.in_vblank = false; - VBL_INT = false; - } - - Core.cpu.LY = LY; - - if (LY==144) - { - Core.in_vblank = true; - } - } - } - else - { - // screen disable sets STAT as though it were vblank, but there is no Stat IRQ asserted - STAT &= 0xFC; - STAT |= 0x01; - - VBL_INT = LYC_INT = HBL_INT = OAM_INT = false; - - Core.in_vblank = true; - - LCD_was_off = true; - - LY = 0; - Core.cpu.LY = LY; - - cycle = 0; - } - - // assert the STAT IRQ line if the line went from zero to 1 - stat_line = VBL_INT | LYC_INT | HBL_INT | OAM_INT; - - if (stat_line && !stat_line_old) - { - if (Core.REG_FFFF.Bit(1)) { Core.cpu.FlagI = true; } - Core.REG_FF0F |= 0x02; - } - - stat_line_old = stat_line; - - // process latch delays - //latch_delay(); - - } - - // might be needed, not sure yet - public void latch_delay() - { - //BGP_l = BGP; - } - - public void OAM_scan(int OAM_cycle) - { - // we are now in STAT mode 2 - // TODO: maybe stat mode 2 flags are set at cycle 0 on visible scanlines? - if (OAM_cycle == 0) - { - OAM_access = false; - OAM_scan_index = 0; - SL_sprites_index = 0; - write_sprite = 0; - } - - // the gameboy has 80 cycles to scan through 40 sprites, picking out the first 10 it finds to draw - // the following is a guessed at implmenentation based on how NES does it, it's probably pretty close - if (OAM_cycle < 10) - { - // start by clearing the sprite table (probably just clears X on hardware, but let's be safe here.) - SL_sprites[OAM_cycle * 4] = 0; - SL_sprites[OAM_cycle * 4 + 1] = 0; - SL_sprites[OAM_cycle * 4 + 2] = 0; - SL_sprites[OAM_cycle * 4 + 3] = 0; - } - else - { - if (write_sprite == 0) - { - if (OAM_scan_index < 40) - { - // (sprite Y - 16) equals LY, we have a sprite - if ((Core.OAM[OAM_scan_index * 4] - 16) <= LY && - ((Core.OAM[OAM_scan_index * 4] - 16) + 8 + (LCDC.Bit(2) ? 8 : 0)) > LY) - { - // always pick the first 10 in range sprites - if (SL_sprites_index < 10) - { - SL_sprites[SL_sprites_index * 4] = Core.OAM[OAM_scan_index * 4]; - - write_sprite = 1; - } - else - { - // if we already have 10 sprites, there's nothing to do, increment the index - OAM_scan_index++; - } - } - else - { - OAM_scan_index++; - } - } - } - else - { - SL_sprites[SL_sprites_index * 4 + write_sprite] = Core.OAM[OAM_scan_index * 4 + write_sprite]; - write_sprite++; - - if (write_sprite == 4) - { - write_sprite = 0; - SL_sprites_index++; - OAM_scan_index++; - } - } - } - } - - public void render(int render_cycle) - { - // we are now in STAT mode 3 - // NOTE: presumably the first necessary sprite is fetched at sprite evaulation - // i.e. just keeping track of the lowest x-value sprite - if (render_cycle == 0) - { - STAT &= 0xFC; - STAT |= 0x03; - OAM_INT = false; - - OAM_access = false; - VRAM_access = false; - OAM_scan_index = 0; - read_case = 0; - internal_cycle = 0; - pre_render = true; - tile_inc = 0; - pixel_counter = 0; - sl_use_index = 0; - index_used = 0; - bottom_index = 0; - sprite_ordered_index = 0; - fetch_sprite = false; - no_sprites = false; - - // calculate the row number of the tiles to be fetched - y_tile = ((int)Math.Floor((float)(scroll_y + LY) / 8)) % 32; - - if (SL_sprites_index == 0) - { - no_sprites = true; - } - } - - if (!pre_render && !fetch_sprite) - { - // start by fetching all the sprites that need to be fetched - if (!no_sprites) - { - for (int i = 0; i < SL_sprites_index; i++) - { - if ((pixel_counter >= (SL_sprites[i * 4 + 1] - 8)) && - (pixel_counter < SL_sprites[i * 4 + 1]) && - !index_used.Bit(i)) - { - fetch_sprite = true; - sprite_fetch_index = 0; - } - } - } - - if (!fetch_sprite) - { - // start shifting data into the LCD - if (render_counter >= (render_offset + 8)) - { - pixel = tile_data_latch[0].Bit(7 - (render_counter % 8)) ? 1 : 0; - pixel |= tile_data_latch[1].Bit(7 - (render_counter % 8)) ? 2 : 0; - pixel = (BGP >> (pixel * 2)) & 3; - // now we have the BG pixel, we next need the sprite pixel - if (!no_sprites) - { - bool have_sprite = false; - int i = bottom_index; - int s_pixel = 0; - int sprite_attr = 0; - - while (i < sprite_ordered_index) - { - if (SL_sprites_ordered[i * 4] == pixel_counter) - { - bottom_index++; - if (bottom_index == SL_sprites_index) { no_sprites = true; } - } - else if (!have_sprite) - { - // we can use the current sprite, so pick out a pixel for it - int t_index = pixel_counter - (SL_sprites_ordered[i * 4] - 8); - - t_index = 7 - t_index; - - sprite_data[0] = (byte)((SL_sprites_ordered[i * 4 + 1] >> t_index) & 1); - sprite_data[1] = (byte)(((SL_sprites_ordered[i * 4 + 2] >> t_index) & 1) << 1); - - s_pixel = sprite_data[0] + sprite_data[1]; - sprite_attr = SL_sprites_ordered[i * 4 + 3]; - - // pixel color of 0 is transparent, so if this is the case we dont have a pixel - if (s_pixel != 0) - { - have_sprite = true; - } - } - i++; - } - - if (have_sprite) - { - bool use_sprite = false; - if (LCDC.Bit(1)) - { - if (!sprite_attr.Bit(7)) - { - if (s_pixel != 0) { use_sprite = true; } - } - else if (pixel == 0) - { - use_sprite = true; - } - - if (!LCDC.Bit(0)) - { - use_sprite = true; - } - } - - if (use_sprite) - { - if (sprite_attr.Bit(4)) - { - pixel = (obj_pal_1 >> (s_pixel * 2)) & 3; - } - else - { - pixel = (obj_pal_0 >> (s_pixel * 2)) & 3; - } - } - } - } - - // based on sprite priority and pixel values, pick a final pixel color - Core._vidbuffer[LY * 160 + pixel_counter] = (int)GBHawk.color_palette[pixel]; - pixel_counter++; - - if (pixel_counter == 160) - { - read_case = 8; - hbl_set_once = true; - } - } - render_counter++; - } - } - - if (!fetch_sprite) - { - if (latch_new_data) - { - latch_new_data = false; - tile_data_latch[0] = tile_data[0]; - tile_data_latch[1] = tile_data[1]; - } - - switch (read_case) - { - case 0: // read a background tile - if ((internal_cycle % 2) == 0) - { - - temp_fetch = y_tile * 32 + (x_tile + tile_inc) % 32; - tile_byte = LCDC.Bit(3) ? Core.BG_map_2[temp_fetch] : Core.BG_map_1[temp_fetch]; - - } - else - { - if (!pre_render) - { - tile_inc++; - } - read_case = 1; - } - break; - - case 1: // read from tile graphics (0) - if ((internal_cycle % 2) == 0) - { - y_scroll_offset = (scroll_y + LY) % 8; - - if (LCDC.Bit(4)) - { - tile_data[0] = Core.CHR_RAM[tile_byte * 16 + y_scroll_offset * 2]; - } - else - { - // same as before except now tile byte represents a signed byte - if (tile_byte.Bit(7)) - { - tile_byte -= 256; - } - tile_data[0] = Core.CHR_RAM[0x1000 + tile_byte * 16 + y_scroll_offset * 2]; - } - - } - else - { - read_case = 2; - } - break; - - case 2: // read from tile graphics (1) - if ((internal_cycle % 2) == 0) - { - y_scroll_offset = (scroll_y + LY) % 8; - - if (LCDC.Bit(4)) - { - // if LCDC somehow changed between the two reads, make sure we have a positive number - if (tile_byte < 0) - { - tile_byte += 256; - } - - tile_data[1] = Core.CHR_RAM[tile_byte * 16 + y_scroll_offset * 2 + 1]; - } - else - { - // same as before except now tile byte represents a signed byte - if (tile_byte.Bit(7) && tile_byte > 0) - { - tile_byte -= 256; - } - - tile_data[1] = Core.CHR_RAM[0x1000 + tile_byte * 16 + y_scroll_offset * 2 + 1]; - } - - } - else - { - if (pre_render) - { - // here we set up rendering - pre_render = false; - render_offset = scroll_x % 8; - render_counter = -1; - latch_counter = 0; - read_case = 0; - } - else - { - read_case = 3; - } - - } - break; - - case 3: // read from sprite data - if ((internal_cycle % 2) == 0) - { - // nothing to do if not fetching - } - else - { - read_case = 0; - latch_new_data = true; - } - break; - - case 4: // read from window data - break; - - case 6: // read from tile graphics (for the window) - break; - - case 7: // read from tile graphics (for the window) - break; - - case 8: // done reading, we are now in phase 0 - - OAM_access = true; - VRAM_access = true; - - STAT &= 0xFC; - STAT |= 0x00; - pre_render = true; - if (hbl_set_once) - { - if (STAT.Bit(3)) { HBL_INT = true; } - hbl_set_once = false; - } - - break; - } - - internal_cycle++; - } - - if (fetch_sprite) - { - if (sprite_fetch_index < SL_sprites_index) - { - if (pixel_counter != 0) { - if ((pixel_counter == (SL_sprites[sprite_fetch_index * 4 + 1] - 8)) && - //(pixel_counter < SL_sprites[sprite_fetch_index * 4 + 1]) && - !index_used.Bit(sprite_fetch_index)) - { - sl_use_index = sprite_fetch_index; - process_sprite(); - SL_sprites_ordered[sprite_ordered_index * 4] = SL_sprites[sprite_fetch_index * 4 + 1]; - SL_sprites_ordered[sprite_ordered_index * 4 + 1] = sprite_sel[0]; - SL_sprites_ordered[sprite_ordered_index * 4 + 2] = sprite_sel[1]; - SL_sprites_ordered[sprite_ordered_index * 4 + 3] = SL_sprites[sprite_fetch_index * 4 + 3]; - sprite_ordered_index++; - index_used |= (1 << sl_use_index); - } - sprite_fetch_index++; - if (sprite_fetch_index == SL_sprites_index) { fetch_sprite = false; } - } - else - { - // whan pixel counter is 0, we want to scan all the points before 0 as well - // certainly non-physical but good enough for now - for (int j = -7; j < 1; j++) - { - for (int i = 0; i < SL_sprites_index; i++) - { - if ((j == (SL_sprites[i * 4 + 1] - 8)) && - !index_used.Bit(i)) - { - sl_use_index = i; - process_sprite(); - SL_sprites_ordered[sprite_ordered_index * 4] = SL_sprites[i * 4 + 1]; - SL_sprites_ordered[sprite_ordered_index * 4 + 1] = sprite_sel[0]; - SL_sprites_ordered[sprite_ordered_index * 4 + 2] = sprite_sel[1]; - SL_sprites_ordered[sprite_ordered_index * 4 + 3] = SL_sprites[i * 4 + 3]; - sprite_ordered_index++; - index_used |= (1 << sl_use_index); - } - } - } - fetch_sprite = false; - } - } - } - } - - public void Reset() - { - LCDC = 0; - STAT = 0x80; - scroll_y = 0; - scroll_x = 0; - LY = 0; - LYC = 0; - DMA_addr = 0; - BGP = 0; - obj_pal_0 = 0; - obj_pal_1 = 0; - window_y = 0; - window_x = 0; - LY_inc = 1; - - cycle = 0; - LYC_INT = false; - HBL_INT = false; - VBL_INT = false; - OAM_INT = false; - - stat_line = false; - stat_line_old = false; - } - - public void process_sprite() - { - int y; - - if (SL_sprites[sl_use_index * 4 + 3].Bit(6)) - { - if (LCDC.Bit(2)) - { - y = LY - (SL_sprites[sl_use_index * 4] - 16); - y = 15 - y; - sprite_sel[0] = Core.CHR_RAM[(SL_sprites[sl_use_index * 4 + 2] & 0xFE) * 16 + y * 2]; - sprite_sel[1] = Core.CHR_RAM[(SL_sprites[sl_use_index * 4 + 2] & 0xFE) * 16 + y * 2 + 1]; - } - else - { - y = LY - (SL_sprites[sl_use_index * 4] - 16); - y = 7 - y; - sprite_sel[0] = Core.CHR_RAM[SL_sprites[sl_use_index * 4 + 2] * 16 + y * 2]; - sprite_sel[1] = Core.CHR_RAM[SL_sprites[sl_use_index * 4 + 2] * 16 + y * 2 + 1]; - } - } - else - { - if (LCDC.Bit(2)) - { - y = LY - (SL_sprites[sl_use_index * 4] - 16); - sprite_sel[0] = Core.CHR_RAM[(SL_sprites[sl_use_index * 4 + 2] & 0xFE) * 16 + y * 2]; - sprite_sel[1] = Core.CHR_RAM[(SL_sprites[sl_use_index * 4 + 2] & 0xFE) * 16 + y * 2 + 1]; - } - else - { - y = LY - (SL_sprites[sl_use_index * 4] - 16); - sprite_sel[0] = Core.CHR_RAM[SL_sprites[sl_use_index * 4 + 2] * 16 + y * 2]; - sprite_sel[1] = Core.CHR_RAM[SL_sprites[sl_use_index * 4 + 2] * 16 + y * 2 + 1]; - } - } - - if (SL_sprites[sl_use_index * 4 + 3].Bit(5)) - { - int b0, b1, b2, b3, b4, b5, b6, b7 = 0; - for (int i = 0; i < 2; i++) - { - b0 = (sprite_sel[i] & 0x01) << 7; - b1 = (sprite_sel[i] & 0x02) << 5; - b2 = (sprite_sel[i] & 0x04) << 3; - b3 = (sprite_sel[i] & 0x08) << 1; - b4 = (sprite_sel[i] & 0x10) >> 1; - b5 = (sprite_sel[i] & 0x20) >> 3; - b6 = (sprite_sel[i] & 0x40) >> 5; - b7 = (sprite_sel[i] & 0x80) >> 7; - - sprite_sel[i] = (byte)(b0 | b1 | b2 | b3 | b4 | b5 | b6 | b7); - } - } - } - - public void SyncState(Serializer ser) - { - ser.Sync("LCDC", ref LCDC); - ser.Sync("STAT", ref STAT); - ser.Sync("scroll_y", ref scroll_y); - ser.Sync("scroll_x", ref scroll_x); - ser.Sync("LY", ref LY); - ser.Sync("LYinc", ref LY_inc); - ser.Sync("LYC", ref LYC); - ser.Sync("DMA_addr", ref DMA_addr); - ser.Sync("BGP", ref BGP); - ser.Sync("obj_pal_0", ref obj_pal_0); - ser.Sync("obj_pal_1", ref obj_pal_1); - ser.Sync("window_y", ref window_y); - ser.Sync("window_x", ref window_x); - ser.Sync("DMA_start", ref DMA_start); - ser.Sync("DMA_clock", ref DMA_clock); - ser.Sync("DMA_inc", ref DMA_inc); - ser.Sync("DMA_byte", ref DMA_byte); - - ser.Sync("LYC_INT", ref LYC_INT); - ser.Sync("HBL_INT", ref HBL_INT); - ser.Sync("VBL_INT", ref VBL_INT); - ser.Sync("OAM_INT", ref OAM_INT); - ser.Sync("stat_line", ref stat_line); - ser.Sync("stat_line_old", ref stat_line_old); - ser.Sync("hbl_set_once", ref hbl_set_once); - ser.Sync("LCD_was_off", ref LCD_was_off); - ser.Sync("OAM_access", ref OAM_access); - ser.Sync("OAM_scan_index", ref OAM_scan_index); - ser.Sync("SL_sprites_index", ref SL_sprites_index); - ser.Sync("SL_sprites", ref SL_sprites, false); - ser.Sync("write_sprite", ref write_sprite); - - ser.Sync("VRAM_access", ref VRAM_access); - ser.Sync("read_case", ref read_case); - ser.Sync("internal_cycle", ref internal_cycle); - ser.Sync("y_tile", ref y_tile); - ser.Sync("y_scroll_offset", ref y_scroll_offset); - ser.Sync("x_tile", ref x_tile); - ser.Sync("x_scroll_offset", ref x_scroll_offset); - ser.Sync("tile_byte", ref tile_byte); - ser.Sync("sprite_fetch_cycles", ref sprite_fetch_cycles); - ser.Sync("fetch_sprite", ref fetch_sprite); - ser.Sync("temp_fetch", ref temp_fetch); - ser.Sync("tile_inc", ref tile_inc); - ser.Sync("pre_render", ref pre_render); - ser.Sync("tile_data", ref tile_data, false); - ser.Sync("tile_data_latch", ref tile_data_latch, false); - ser.Sync("latch_counter", ref latch_counter); - ser.Sync("latch_new_data", ref latch_new_data); - ser.Sync("render_counter", ref render_counter); - ser.Sync("render_offset", ref render_offset); - ser.Sync("pixel_counter", ref pixel_counter); - ser.Sync("pixel", ref pixel); - ser.Sync("sprite_data", ref sprite_data, false); - ser.Sync("sl_use_index", ref sl_use_index); - ser.Sync("sprite_sel", ref sprite_sel, false); - ser.Sync("no_sprites", ref no_sprites); - ser.Sync("sprite_fetch_index", ref sprite_fetch_index); - ser.Sync("SL_sprites_ordered", ref SL_sprites_ordered, false); - ser.Sync("index_used", ref index_used); - ser.Sync("sprite_ordered_index", ref sprite_ordered_index); - ser.Sync("bottom_index", ref bottom_index); - - } - } -} diff --git a/Timer.cs b/Timer.cs deleted file mode 100644 index b243081d70..0000000000 --- a/Timer.cs +++ /dev/null @@ -1,175 +0,0 @@ -using BizHawk.Common; -using BizHawk.Common.NumberExtensions; -using System; - -namespace BizHawk.Emulation.Cores.Nintendo.GBHawk -{ - // Timer Emulation - public class Timer - { - public GBHawk Core { get; set; } - - public ushort divider_reg; - public byte timer_reload; - public byte timer; - public byte timer_old; - public byte timer_control; - public byte pending_reload; - public byte write_ignore; - public bool old_state; - public bool state; - public bool reload_block; - public bool TMA_coincidence; - - public byte ReadReg(int addr) - { - byte ret = 0; - - switch (addr) - { - case 0xFF04: ret = (byte)(divider_reg >> 8); break; // DIV register - case 0xFF05: ret = timer; break; // TIMA (Timer Counter) - case 0xFF06: ret = timer_reload; break; // TMA (Timer Modulo) - case 0xFF07: ret = timer_control; break; // TAC (Timer Control) - } - - return ret; - } - - public void WriteReg(int addr, byte value) - { - switch (addr) - { - // DIV register - case 0xFF04: - divider_reg = 0; - break; - - // TIMA (Timer Counter) - case 0xFF05: - if (write_ignore == 0) - { - timer_old = timer; - timer = value; - reload_block = true; - } - break; - - // TMA (Timer Modulo) - case 0xFF06: - timer_reload = value; - if (TMA_coincidence) - { - timer = timer_reload; - timer_old = timer; - } - break; - - // TAC (Timer Control) - case 0xFF07: - timer_control = (byte)((timer_control & 0xf8) | (value & 0x7)); // only bottom 3 bits function - break; - } - } - - public void tick_1() - { - if (write_ignore > 0) - { - write_ignore--; - if (write_ignore==0) - { - TMA_coincidence = false; - } - } - - if (pending_reload > 0) - { - pending_reload--; - if (pending_reload == 0 && !reload_block) - { - timer = timer_reload; - timer_old = timer; - write_ignore = 4; - TMA_coincidence = true; - - // set interrupts - if (Core.REG_FFFF.Bit(2)) { Core.cpu.FlagI = true; } - Core.REG_FF0F |= 0x04; - } - } - } - - public void tick_2() - { - divider_reg++; - - // pick a bit to test based on the current value of timer control - switch (timer_control & 3) - { - case 0: - state = divider_reg.Bit(9); - break; - case 1: - state = divider_reg.Bit(3); - break; - case 2: - state = divider_reg.Bit(5); - break; - case 3: - state = divider_reg.Bit(7); - break; - } - - // And it with the state of the timer on/off bit - state &= timer_control.Bit(2); - - // this procedure allows several glitchy timer ticks, since it only measures falling edge of the state - // so things like turning the timer off and resetting the divider will tick the timer - if (old_state && !state) - { - timer_old = timer; - timer++; - - // if overflow, set the interrupt flag and reload the timer (4 clocks later) - if (timer < timer_old) - { - pending_reload = 4; - reload_block = false; - } - } - - old_state = state; - } - - public void Reset() - { - divider_reg = 0; - timer_reload = 0; - timer = 0; - timer_old = 0; - timer_control = 0xF8; - pending_reload = 0; - write_ignore = 0; - old_state = false; - state = false; - reload_block = false; - TMA_coincidence = false; - } - - public void SyncState(Serializer ser) - { - ser.Sync("divider_reg", ref divider_reg); - ser.Sync("timer_reload", ref timer_reload); - ser.Sync("timer", ref timer); - ser.Sync("timer_old", ref timer_old); - ser.Sync("timer_control", ref timer_control); - ser.Sync("pending_reload", ref pending_reload); - ser.Sync("write_ignore", ref write_ignore); - ser.Sync("old_state", ref old_state); - ser.Sync("state", ref state); - ser.Sync("reload_block", ref reload_block); - ser.Sync("TMA_coincidence", ref TMA_coincidence); - } - } -} \ No newline at end of file