CDL - support GPGX. still need to make enable toggle, to win back speed

This commit is contained in:
zeromus 2015-10-27 16:31:43 -05:00
parent e8d307c33a
commit 35b6d8c1d6
16 changed files with 295 additions and 2 deletions

View File

@ -406,6 +406,7 @@
this.ShowMenuContextMenuSeparator = new System.Windows.Forms.ToolStripSeparator();
this.ShowMenuContextMenuItem = new System.Windows.Forms.ToolStripMenuItem();
this.timerMouseIdle = new System.Windows.Forms.Timer(this.components);
this.toolStripMenuItem18 = new System.Windows.Forms.ToolStripMenuItem();
this.MainformMenu.SuspendLayout();
this.MainStatusBar.SuspendLayout();
this.MainFormContextMenu.SuspendLayout();
@ -2816,6 +2817,7 @@
this.GenesisSubMenu.DropDownItems.AddRange(new System.Windows.Forms.ToolStripItem[] {
this.vDPViewerToolStripMenuItem,
this.GenesisGameGenieECDC,
this.toolStripMenuItem18,
this.toolStripSeparator26,
this.GenesisSettingsToolStripMenuItem});
this.GenesisSubMenu.Name = "GenesisSubMenu";
@ -3586,6 +3588,13 @@
this.timerMouseIdle.Interval = 2000;
this.timerMouseIdle.Tick += new System.EventHandler(this.timerMouseIdle_Tick);
//
// toolStripMenuItem18
//
this.toolStripMenuItem18.Name = "toolStripMenuItem18";
this.toolStripMenuItem18.Size = new System.Drawing.Size(217, 22);
this.toolStripMenuItem18.Text = "Code-Data Logger";
this.toolStripMenuItem18.Click += new System.EventHandler(this.CodeDataLoggerMenuItem_Click);
//
// MainForm
//
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.None;
@ -4003,6 +4012,7 @@
private System.Windows.Forms.ToolStripMenuItem C64SubMenu;
private System.Windows.Forms.ToolStripMenuItem C64SettingsMenuItem;
private System.Windows.Forms.ToolStripMenuItem toolStripMenuItem16;
private System.Windows.Forms.ToolStripMenuItem toolStripMenuItem18;
}
}

View File

@ -10,6 +10,8 @@ using BizHawk.Emulation.Common.IEmulatorExtensions;
using BizHawk.Emulation.Cores.Nintendo.Gameboy;
using BizHawk.Emulation.Cores.Components.H6280;
using BizHawk.Emulation.Cores.PCEngine;
using BizHawk.Emulation.Cores.Consoles.Sega;
using BizHawk.Emulation.Cores.Consoles.Sega.gpgx;
using BizHawk.Client.Common;
using BizHawk.Client.EmuHawk.ToolExtensions;
@ -79,6 +81,15 @@ namespace BizHawk.Client.EmuHawk
else
LoggingActiveCheckbox.Checked = _cdl.Active;
}
else if (_emu is GPGX)
{
var gpgx = _emu as GPGX;
_cdl = gpgx.CDL;
if (_cdl == null)
LoggingActiveCheckbox.Checked = false;
else
LoggingActiveCheckbox.Checked = _cdl.Active;
}
UpdateDisplay();
}
@ -162,6 +173,18 @@ namespace BizHawk.Client.EmuHawk
}
gambatte.CDL = cdl_gb;
}
else if (_emu is GPGX)
{
var gpgx = _emu as GPGX;
var cdl_gb = newCDL as CodeDataLog_GEN;
var memd = gpgx.AsMemoryDomains();
if (!cdl_gb.CheckConsistency(memd))
{
MessageBox.Show(this, "CDL file does not match emulator's current memory map!");
return;
}
gpgx.CDL = cdl_gb;
}
}
UpdateDisplay();
@ -206,6 +229,14 @@ namespace BizHawk.Client.EmuHawk
gambatte.CDL = cdl_gb;
_cdl = cdl_gb;
}
else if (_emu is GPGX)
{
var gpgx = _emu as GPGX;
var memd = gpgx.AsMemoryDomains();
var cdl_gen = CodeDataLog_GEN.Create(memd);
gpgx.CDL = cdl_gen;
_cdl = cdl_gen;
}
UpdateDisplay();
}

View File

@ -758,6 +758,7 @@
<Compile Include="Consoles\PC Engine\PCEngine.Input.cs" />
<Compile Include="Consoles\PC Engine\PCEngine.TurboCD.cs" />
<Compile Include="Consoles\PC Engine\ScsiCDBus.cs" />
<Compile Include="Consoles\Sega\CodeDataLog_GEN.cs" />
<Compile Include="Consoles\Sega\Genesis\Cart\EEPROM.cs" />
<Compile Include="Consoles\Sega\Genesis\Cart\RomHeader.cs" />
<Compile Include="Consoles\Sega\Genesis\Cart\SaveRAM.cs" />

View File

@ -8,6 +8,7 @@ using BizHawk.Emulation.Common;
//needed for being a factory
using BizHawk.Emulation.Cores.Nintendo.Gameboy;
using BizHawk.Emulation.Cores.Components.H6280;
using BizHawk.Emulation.Cores.Consoles.Sega;
namespace BizHawk.Emulation.Cores.Components.H6280
{
@ -83,6 +84,8 @@ namespace BizHawk.Emulation.Cores.Components.H6280
return new CodeDataLog_PCE().Load(br);
else if(FileSubType == "GB")
return new CodeDataLog_GB().Load(br);
else if (FileSubType == "GEN")
return new CodeDataLog_GEN().Load(br);
else return null;
}

View File

@ -1,8 +1,6 @@
using BizHawk.Emulation.Common;
using BizHawk.Emulation.Cores.Components.H6280;
//TODO - refactor into different files
namespace BizHawk.Emulation.Cores.Nintendo.Gameboy
{
public class CodeDataLog_GB : CodeDataLog
@ -30,6 +28,7 @@ namespace BizHawk.Emulation.Cores.Nintendo.Gameboy
{
if (memdomains["ROM"].Size != this["ROM"].Length) return false;
if (memdomains["WRAM"].Size != this["WRAM"].Length) return false;
if (memdomains.Has("CartRAM") != this.ContainsKey("CartRAM")) return false;
if(memdomains.Has("CartRAM"))
if (memdomains["CartRAM"].Size != this["CartRAM"].Length)
return false;

View File

@ -0,0 +1,38 @@
using BizHawk.Emulation.Common;
using BizHawk.Emulation.Cores.Components.H6280;
namespace BizHawk.Emulation.Cores.Consoles.Sega
{
public class CodeDataLog_GEN : CodeDataLog
{
public static CodeDataLog_GEN Create(IMemoryDomains memdomains)
{
var t = new CodeDataLog_GEN();
t["MD CART"] = new byte[memdomains["MD CART"].Size];
t["68K RAM"] = new byte[memdomains["68K RAM"].Size];
t["Z80 RAM"] = new byte[memdomains["Z80 RAM"].Size];
if(memdomains.Has("SRAM"))
t["SRAM"] = new byte[memdomains["SRAM"].Size];
return t;
}
public override string SubType { get { return "GEN"; } }
public override int SubVer { get { return 0; } }
//todo - this could be base classed
public bool CheckConsistency(IMemoryDomains memdomains)
{
if (memdomains["MD CART"].Size != this["MD CART"].Length) return false;
if (memdomains["68K RAM"].Size != this["68K RAM"].Length) return false;
if (memdomains["Z80 RAM"].Size != this["Z80 RAM"].Length) return false;
if (memdomains.Has("SRAM") != this.ContainsKey("SRAM")) return false;
if (memdomains.Has("SRAM"))
if (memdomains["SRAM"].Size != this["SRAM"].Length)
return false;
return true;
}
}
}

View File

@ -170,6 +170,10 @@ namespace BizHawk.Emulation.Cores.Consoles.Sega.gpgx
PutSettings((GPGXSettings)Settings ?? new GPGXSettings());
//TODO - this hits performance, we need to make it controllable
CDCallback = new LibGPGX.CDCallback(CDCallbackProc);
LibGPGX.gpgx_set_cd_callback(CDCallback);
InitMemCallbacks();
KillMemCallbacks();
}
@ -180,6 +184,23 @@ namespace BizHawk.Emulation.Cores.Consoles.Sega.gpgx
}
}
public CodeDataLog_GEN CDL;
void CDCallbackProc(int addr, LibGPGX.CDLog_AddrType addrtype, LibGPGX.CDLog_Flags flags)
{
if (CDL == null) return;
if (!CDL.Active) return;
string key;
switch (addrtype)
{
case LibGPGX.CDLog_AddrType.MDCART: key = "MD CART"; break;
case LibGPGX.CDLog_AddrType.RAM68k: key = "68K RAM"; break;
case LibGPGX.CDLog_AddrType.RAMZ80: key = "Z80 RAM"; break;
case LibGPGX.CDLog_AddrType.SRAM: key = "SRAM"; break;
default: throw new InvalidOperationException("Lagrangian earwax incident");
}
CDL[key][addr] |= (byte)flags;
}
public IEmulatorServiceProvider ServiceProvider { get; private set; }
public bool DriveLightEnabled { get; private set;}
@ -671,6 +692,7 @@ namespace BizHawk.Emulation.Cores.Consoles.Sega.gpgx
LibGPGX.mem_cb ExecCallback;
LibGPGX.mem_cb ReadCallback;
LibGPGX.mem_cb WriteCallback;
LibGPGX.CDCallback CDCallback;
void InitMemCallbacks()
{

View File

@ -109,6 +109,24 @@ namespace BizHawk.Emulation.Cores.Consoles.Sega.gpgx
DEVICE_ACTIVATOR = 0x0a,// Activator
};
public enum CDLog_AddrType
{
MDCART, RAM68k, RAMZ80, SRAM,
};
[Flags]
public enum CDLog_Flags
{
Exec68k = 0x01,
Data68k = 0x04,
ExecZ80First = 0x08,
ExecZ80Operand = 0x10,
DataZ80 = 0x20,
DMASource = 0x40,
};
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
public delegate void input_cb();
@ -118,9 +136,17 @@ namespace BizHawk.Emulation.Cores.Consoles.Sega.gpgx
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
public delegate void mem_cb(uint addr);
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
public delegate void CDCallback(int addr, CDLog_AddrType addrtype, CDLog_Flags flags);
[DllImport("libgenplusgx.dll", CallingConvention = CallingConvention.Cdecl)]
public static extern void gpgx_set_mem_callback(mem_cb read, mem_cb write, mem_cb exec);
[DllImport("libgenplusgx.dll", CallingConvention = CallingConvention.Cdecl)]
public static extern void gpgx_set_cd_callback(CDCallback cd);
/// <summary>
/// not every flag is valid for every device!
/// </summary>

View File

@ -1,8 +1,28 @@
#ifndef CALLBACKS_H
#define CALLBACKS_H
#include "types.h"
typedef void (*CDCallback)(int32 addr, int32 addrtype, int32 flags);
extern void (*biz_execcb)(unsigned addr);
extern void (*biz_readcb)(unsigned addr);
extern void (*biz_writecb)(unsigned addr);
extern CDCallback biz_cdcallback;
enum eCDLog_AddrType
{
eCDLog_AddrType_MDCART, eCDLog_AddrType_RAM68k, eCDLog_AddrType_RAMZ80, eCDLog_AddrType_SRAM,
};
enum eCDLog_Flags
{
eCDLog_Flags_Exec68k = 0x01,
eCDLog_Flags_Data68k = 0x04,
eCDLog_Flags_ExecZ80First = 0x08,
eCDLog_Flags_ExecZ80Operand = 0x10,
eCDLog_Flags_DataZ80 = 0x20,
eCDLog_Flags_DMASource = 0x40
};
#endif

View File

@ -56,6 +56,7 @@ extern void zap(void);
void (*biz_execcb)(unsigned addr) = NULL;
void (*biz_readcb)(unsigned addr) = NULL;
void (*biz_writecb)(unsigned addr) = NULL;
CDCallback biz_cdcallback = NULL;
static void update_viewport(void)
{
@ -545,6 +546,11 @@ GPGX_EX void gpgx_set_mem_callback(void (*read)(unsigned), void (*write)(unsigne
biz_execcb = exec;
}
GPGX_EX void gpgx_set_cd_callback(CDCallback cdcallback)
{
biz_cdcallback = cdcallback;
}
GPGX_EX void gpgx_set_draw_mask(int mask)
{
cinterface_render_bga = !!(mask & 1);

View File

@ -20,6 +20,7 @@ extern int vdp_68k_irq_ack(int int_level);
#include "m68kconf.h"
#include "m68kcpu.h"
#include "m68kops.h"
#include "shared.h"
/* ======================================================================== */
/* ================================= DATA ================================= */
@ -255,6 +256,53 @@ void m68k_set_irq_delay(unsigned int int_level)
m68ki_check_interrupts(); /* Level triggered (IRQ) */
}
extern uint8 work_ram[0x10000]; /* 68K RAM */
void CDLog68k(uint addr, uint flags)
{
addr &= 0x00FFFFFF;
//check for sram region first
if(sram.on)
{
if(addr >= sram.start && addr <= sram.end)
{
biz_cdcallback(addr - sram.start, eCDLog_AddrType_SRAM, flags);
return;
}
}
if(addr < 0x400000)
{
uint block64k_rom;
//apply memory map to process rom address
unsigned char* block64k = m68ki_cpu.memory_map[((addr)>>16)&0xff].base;
//outside the ROM range. complex mapping logic/accessories; not sure how to handle any of this
if(block64k < cart.rom || block64k >= cart.rom + cart.romsize)
return;
block64k_rom = block64k - cart.rom;
addr = ((addr) & 0xffff) + block64k_rom;
//outside the ROM range somehow
if(addr >= cart.romsize)
return;
biz_cdcallback(addr, eCDLog_AddrType_MDCART, flags);
return;
}
if(addr > 0xFF0000)
{
//no memory map needed
biz_cdcallback(addr & 0xFFFF, eCDLog_AddrType_RAM68k, flags);
return;
}
}
void m68k_run(unsigned int cycles)
{
/* Make sure CPU is not already ahead */
@ -294,6 +342,13 @@ void m68k_run(unsigned int cycles)
if (biz_execcb)
biz_execcb(REG_PC);
if(biz_cdcallback)
{
CDLog68k(REG_PC,eCDLog_Flags_Exec68k);
CDLog68k(REG_PC+1,eCDLog_Flags_Exec68k);
}
/* Decode next instruction */
REG_IR = m68ki_read_imm_16();

View File

@ -16,6 +16,7 @@
#include "m68k.h"
#include "../cinterface/callbacks.h"
void CDLog68k(uint addr, uint flags);
/* ======================================================================== */
/* ============================ GENERAL DEFINES =========================== */
@ -871,6 +872,9 @@ INLINE uint m68ki_read_8_fc(uint address, uint fc)
if (biz_readcb)
biz_readcb(address);
if(biz_cdcallback)
CDLog68k(address,eCDLog_Flags_Data68k);
m68ki_set_fc(fc) /* auto-disable (see m68kcpu.h) */
if (temp->read8) return (*temp->read8)(ADDRESS_68K(address));
@ -883,6 +887,12 @@ INLINE uint m68ki_read_16_fc(uint address, uint fc)
if (biz_readcb)
biz_readcb(address);
if(biz_cdcallback)
{
CDLog68k(address,eCDLog_Flags_Data68k);
CDLog68k(address+1,eCDLog_Flags_Data68k);
}
m68ki_set_fc(fc) /* auto-disable (see m68kcpu.h) */
m68ki_check_address_error(address, MODE_READ, fc) /* auto-disable (see m68kcpu.h) */
@ -897,6 +907,14 @@ INLINE uint m68ki_read_32_fc(uint address, uint fc)
if (biz_readcb)
biz_readcb(address);
if(biz_cdcallback)
{
CDLog68k(address,eCDLog_Flags_Data68k);
CDLog68k(address+1,eCDLog_Flags_Data68k);
CDLog68k(address+2,eCDLog_Flags_Data68k);
CDLog68k(address+3,eCDLog_Flags_Data68k);
}
m68ki_set_fc(fc) /* auto-disable (see m68kcpu.h) */
m68ki_check_address_error(address, MODE_READ, fc) /* auto-disable (see m68kcpu.h) */

View File

@ -1,3 +1,6 @@
#ifndef _TYPES_H
#define _TYPES_H
#undef uint8
#undef uint16
#undef uint32
@ -27,3 +30,5 @@ typedef union
} byte;
} reg16_t;
#endif

View File

@ -41,6 +41,7 @@
#include "shared.h"
#include "hvc.h"
#include "../cinterface/callbacks.h"
/* Mark a pattern as modified */
#define MARK_BG_DIRTY(addr) \
@ -3021,6 +3022,8 @@ static void vdp_z80_data_w_sg(unsigned int data)
/* DMA operations (Mega Drive VDP only) */
/*--------------------------------------------------------------------------*/
void CDLog68k(uint addr, uint flags);
/* DMA from 68K bus: $000000-$7FFFFF (external area) */
static void vdp_dma_68k_ext(unsigned int length)
{
@ -3040,6 +3043,16 @@ static void vdp_dma_68k_ext(unsigned int length)
{
data = *(uint16 *)(m68k.memory_map[source>>16].base + (source & 0xFFFF));
}
if(biz_cdcallback)
{
//if((code & 0x0F) == 0x01) //VRAM target //lets handle everything here
{
CDLog68k(source,eCDLog_Flags_DMASource);
CDLog68k(source+1,eCDLog_Flags_DMASource);
}
}
/* Increment source address */
source += 2;

View File

@ -126,6 +126,8 @@
#include "shared.h"
#include "z80.h"
#include "../cinterface/callbacks.h"
/* execute main opcodes inside a big switch statement */
#define BIG_SWITCH 1
@ -632,6 +634,35 @@ INLINE void WM16( UINT32 addr, PAIR *r )
WM((addr+1)&0xffff,r->b.h);
}
void CDLog68k(uint addr, uint flags);
void CDLogZ80(uint addr, uint flags)
{
//in case we wrap around while reading a u16 from FFFF...
addr &= 0xFFFF;
if(addr < 0x4000)
{
addr &= 0x1FFFF;
biz_cdcallback(addr, eCDLog_AddrType_RAMZ80, flags);
return;
}
if(addr >= 0x8000)
{
addr = zbank | (addr & 0x7FFF);
if (zbank_memory_map[addr >> 16].write)
{
//special memory maps are hard to support here.
return;
}
//punt to 68k mapper
CDLog68k(addr, flags);
return;
}
}
/***************************************************************
* ROP() is identical to RM() except it is used for
* reading opcodes. In case of system with memory mapped I/O,
@ -641,6 +672,10 @@ INLINE UINT8 ROP(void)
{
unsigned pc = PCD;
PC++;
if(biz_cdcallback)
CDLogZ80(PC,eCDLog_Flags_ExecZ80First);
return cpu_readop(pc);
}
@ -654,6 +689,10 @@ INLINE UINT8 ARG(void)
{
unsigned pc = PCD;
PC++;
if(biz_cdcallback)
CDLogZ80(pc,eCDLog_Flags_ExecZ80Operand);
return cpu_readop_arg(pc);
}
@ -661,6 +700,13 @@ INLINE UINT32 ARG16(void)
{
unsigned pc = PCD;
PC += 2;
if(biz_cdcallback)
{
CDLogZ80(pc,eCDLog_Flags_ExecZ80Operand);
CDLogZ80(pc+1,eCDLog_Flags_ExecZ80Operand);
}
return cpu_readop_arg(pc) | (cpu_readop_arg((pc+1)&0xffff) << 8);
}

Binary file not shown.