Exemple #1
0
 private void TracerWrapper(string[] content)
 {
     _tracer.Put(new TraceInfo
     {
         Disassembly  = content[0],
         RegisterInfo = content[1]
     });
 }
Exemple #2
0
 private void snes_trace(string disassembly, string registerInfo)
 {
     _tracer.Put(new TraceInfo
     {
         Disassembly  = disassembly,
         RegisterInfo = registerInfo
     });
 }
Exemple #3
0
        private void snes_trace(string msg)
        {
            // TODO: get them out of the core split up and remove this hackery
            string splitStr = "A:";

            var split = msg.Split(new[] { splitStr }, 2, StringSplitOptions.None);

            _tracer.Put(new TraceInfo
            {
                Disassembly  = split[0].PadRight(34),
                RegisterInfo = splitStr + split[1]
            });
        }
Exemple #4
0
        private void snes_trace(uint which, string msg)
        {
            // TODO: get them out of the core split up and remove this hackery
            const string splitStr = "A:";

            if (which == (uint)LibsnesApi.eTRACE.CPU)
            {
                var split = msg.Split(new[] { splitStr }, 2, StringSplitOptions.None);

                _tracer.Put(new TraceInfo
                {
                    Disassembly  = split[0].PadRight(34),
                    RegisterInfo = splitStr + split[1]
                });
            }
            else if (which == (uint)LibsnesApi.eTRACE.SMP)
            {
                int    idx  = msg.IndexOf("YA:");
                string dis  = msg.Substring(0, idx).TrimEnd();
                string regs = msg.Substring(idx);
                _tracer.Put(new TraceInfo
                {
                    Disassembly  = dis,
                    RegisterInfo = regs
                });
            }
            else if (which == (uint)LibsnesApi.eTRACE.GB)
            {
                int    idx  = msg.IndexOf("AF:");
                string dis  = msg.Substring(0, idx).TrimEnd();
                string regs = msg.Substring(idx);
                _tracer.Put(new TraceInfo
                {
                    Disassembly  = dis,
                    RegisterInfo = regs
                });
            }
        }
Exemple #5
0
        private void MakeTrace(int t)
        {
            StringBuilder new_d = new StringBuilder(Disasm_Length);
            StringBuilder new_r = new StringBuilder(Reg_String_Length);

            LibMSX.MSX_getdisassembly(MSX_Pntr, new_d, t, Disasm_Length);
            LibMSX.MSX_getregisterstate(MSX_Pntr, new_r, t, Reg_String_Length);

            Tracer.Put(new TraceInfo
            {
                Disassembly  = new_d.ToString().PadRight(36),
                RegisterInfo = new_r.ToString()
            });
        }
Exemple #6
0
        public void FrameAdvance(bool render, bool rendersound)
        {
            lagged = true;
            Frame++;
            PSG.BeginFrame(Cpu.TotalExecutedCycles);
            Cpu.Debug = Tracer.Enabled;
            if (!IsGameGear)
            {
                PSG.StereoPanning = Settings.ForceStereoSeparation ? ForceStereoByte : (byte)0xFF;
            }

            if (Cpu.Debug && Cpu.Logger == null)             // TODO, lets not do this on each frame. But lets refactor CoreComm/CoreComm first
            {
                Cpu.Logger = (s) => Tracer.Put(s);
            }

            if (IsGameGear == false)
            {
                Cpu.NonMaskableInterrupt = Controller["Pause"];
            }

            if (IsGame3D && Settings.Fix3D)
            {
                Vdp.ExecFrame((Frame & 1) == 0);
            }
            else
            {
                Vdp.ExecFrame(render);
            }

            PSG.EndFrame(Cpu.TotalExecutedCycles);
            if (lagged)
            {
                lagCount++;
                isLag = true;
            }
            else
            {
                isLag = false;
            }
        }
        private void Init(GameInfo game, byte[] rom)
        {
            Cpu  = new HuC6280(MemoryCallbacks);
            VCE  = new VCE();
            VDC1 = new VDC(this, Cpu, VCE);
            PSG  = new HuC6280PSG(735);
            SCSI = new ScsiCDBus(this, disc);

            Cpu.Logger = s => Tracer.Put(s);

            if (TurboGrafx)
            {
                Ram = new byte[0x2000];
                Cpu.ReadMemory21  = ReadMemory;
                Cpu.WriteMemory21 = WriteMemory;
                Cpu.WriteVDC      = VDC1.WriteVDC;
                _soundProvider    = PSG;
                CDAudio           = new CDAudio(null, 0);
            }

            else if (SuperGrafx)
            {
                VDC2              = new VDC(this, Cpu, VCE);
                VPC               = new VPC(this, VDC1, VDC2, VCE, Cpu);
                Ram               = new byte[0x8000];
                Cpu.ReadMemory21  = ReadMemorySGX;
                Cpu.WriteMemory21 = WriteMemorySGX;
                Cpu.WriteVDC      = VDC1.WriteVDC;
                _soundProvider    = PSG;
                CDAudio           = new CDAudio(null, 0);
            }

            else if (TurboCD)
            {
                Ram               = new byte[0x2000];
                CDRam             = new byte[0x10000];
                ADPCM             = new ADPCM(this, SCSI);
                Cpu.ReadMemory21  = ReadMemoryCD;
                Cpu.WriteMemory21 = WriteMemoryCD;
                Cpu.WriteVDC      = VDC1.WriteVDC;
                CDAudio           = new CDAudio(disc);
                SetCDAudioCallback();
                PSG.MaxVolume   = short.MaxValue * 3 / 4;
                SoundMixer      = new SoundMixer(735, PSG, CDAudio, ADPCM);
                _soundProvider  = SoundMixer;
                Cpu.ThinkAction = cycles => { SCSI.Think(); ADPCM.Think(cycles); };
            }

            if (rom.Length == 0x60000)
            {
                // 384k roms require special loading code. Why ;_;
                // In memory, 384k roms look like [1st 256k][Then full 384k]
                RomData = new byte[0xA0000];
                var origRom = rom;
                for (int i = 0; i < 0x40000; i++)
                {
                    RomData[i] = origRom[i];
                }
                for (int i = 0; i < 0x60000; i++)
                {
                    RomData[i + 0x40000] = origRom[i];
                }
                RomLength = RomData.Length;
            }
            else if (rom.Length > 1024 * 1024)
            {
                // If the rom is bigger than 1 megabyte, switch to Street Fighter 2 mapper
                Cpu.ReadMemory21  = ReadMemorySF2;
                Cpu.WriteMemory21 = WriteMemorySF2;
                RomData           = rom;
                RomLength         = RomData.Length;

                // user request: current value of the SF2MapperLatch on the tracelogger
                Cpu.Logger = s => Tracer.Put(new TraceInfo
                {
                    Disassembly  = $"{SF2MapperLatch:X1}:{s}",
                    RegisterInfo = ""
                });
            }
            else
            {
                // normal rom.
                RomData   = rom;
                RomLength = RomData.Length;
            }

            if (game["BRAM"] || Type == NecSystemType.TurboCD)
            {
                BramEnabled = true;
                BRAM        = new byte[2048];

                // pre-format BRAM. damn are we helpful.
                BRAM[0] = 0x48; BRAM[1] = 0x55; BRAM[2] = 0x42; BRAM[3] = 0x4D;
                BRAM[4] = 0x00; BRAM[5] = 0x88; BRAM[6] = 0x10; BRAM[7] = 0x80;
            }

            if (game["SuperSysCard"])
            {
                SuperRam = new byte[0x30000];
            }

            if (game["ArcadeCard"])
            {
                ArcadeRam            = new byte[0x200000];
                ArcadeCard           = true;
                ArcadeCardRewindHack = Settings.ArcadeCardRewindHack;
                for (int i = 0; i < 4; i++)
                {
                    ArcadePage[i] = new ArcadeCardPage();
                }
            }

            if (game["PopulousSRAM"])
            {
                PopulousRAM       = new byte[0x8000];
                Cpu.ReadMemory21  = ReadMemoryPopulous;
                Cpu.WriteMemory21 = WriteMemoryPopulous;
            }

            // the gamedb can force sprite limit on, ignoring settings
            if (game["ForceSpriteLimit"] || game.NotInDatabase)
            {
                ForceSpriteLimit = true;
            }

            if (game["CdVol"])
            {
                CDAudio.MaxVolume = int.Parse(game.OptionValue("CdVol"));
            }

            if (game["PsgVol"])
            {
                PSG.MaxVolume = int.Parse(game.OptionValue("PsgVol"));
            }

            if (game["AdpcmVol"])
            {
                ADPCM.MaxVolume = int.Parse(game.OptionValue("AdpcmVol"));
            }

            // the gamedb can also force equalizevolumes on
            if (TurboCD && (Settings.EqualizeVolume || game["EqualizeVolumes"] || game.NotInDatabase))
            {
                SoundMixer.EqualizeVolumes();
            }

            // Ok, yes, HBlankPeriod's only purpose is game-specific hax.
            // 1) At least they're not coded directly into the emulator, but instead data-driven.
            // 2) The games which have custom HBlankPeriods work without it, the override only
            //    serves to clean up minor gfx anomalies.
            // 3) There's no point in haxing the timing with incorrect values in an attempt to avoid this.
            //    The proper fix is cycle-accurate/bus-accurate timing. That isn't coming to the C#
            //    version of this core. Let's just acknolwedge that the timing is imperfect and fix
            //    it in the least intrusive and most honest way we can.
            if (game["HBlankPeriod"])
            {
                VDC1.HBlankCycles = game.GetIntValue("HBlankPeriod");
            }

            // This is also a hack. Proper multi-res/TV emulation will be a native-code core feature.
            if (game["MultiResHack"])
            {
                VDC1.MultiResHack = game.GetIntValue("MultiResHack");
            }

            Cpu.ResetPC();

            Tracer = new TraceBuffer {
                Header = Cpu.TraceHeader
            };
            var ser = new BasicServiceProvider(this);

            ServiceProvider = ser;
            ser.Register <ITraceable>(Tracer);
            ser.Register <IDisassemblable>(Cpu);
            ser.Register <IVideoProvider>((IVideoProvider)VPC ?? VDC1);
            ser.Register <ISoundProvider>(_soundProvider);
            ser.Register <IStatable>(new StateSerializer(SyncState));
            SetupMemoryDomains();
        }