saturn: connect to bizhawk's existing DiscSystem code. emu should now properly load the .cue given. the hack that redirects every .cue that is not in a gamedb to saturn is still in place; saturn detection heuristics will be coming

This commit is contained in:
goyuken 2013-05-01 00:27:36 +00:00
parent d2fecaa172
commit 368bc58d0a
5 changed files with 223 additions and 12 deletions

View File

@ -32,7 +32,66 @@ namespace BizHawk.Emulation.Consoles.Sega.Saturn
[DllImport("libyabause.dll", CallingConvention = CallingConvention.Cdecl)]
public static extern void libyabause_deinit();
/// <summary>
///
/// </summary>
/// <param name="intf">cd interface. struct need not persist after call, but the function pointers better</param>
/// <returns></returns>
[DllImport("libyabause.dll", CallingConvention = CallingConvention.Cdecl)]
public static extern bool libyabause_init();
public static extern bool libyabause_init(ref CDInterface intf);
public struct CDInterface
{
public int DontTouch;
public IntPtr DontTouch2;
/// <summary>
/// init cd functions
/// </summary>
/// <param name="unused"></param>
/// <returns>0 on success, -1 on failure</returns>
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
public delegate int Init(string unused);
public Init InitFunc;
/// <summary>
/// deinit cd functions
/// </summary>
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
public delegate void DeInit();
public DeInit DeInitFunc;
/// <summary>
/// 0 = cd present, spinning
/// 1 = cd present, not spinning
/// 2 = no cd
/// 3 = tray open
/// </summary>
/// <returns></returns>
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
public delegate int GetStatus();
public GetStatus GetStatusFunc;
/// <summary>
/// read all TOC entries
/// </summary>
/// <param name="dest">place to copy to</param>
/// <returns>number of bytes written. should be 408</returns>
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
public delegate int ReadTOC(IntPtr dest);
public ReadTOC ReadTOCFunc;
/// <summary>
/// read a sector, should be 2352 bytes
/// </summary>
/// <param name="FAD"></param>
/// <param name="dest"></param>
/// <returns></returns>
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
public delegate int ReadSectorFAD(int FAD, IntPtr dest);
public ReadSectorFAD ReadSectorFADFunc;
/// <summary>
/// hint the next sector, for async loading
/// </summary>
/// <param name="FAD"></param>
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
public delegate void ReadAheadFAD(int FAD);
public ReadAheadFAD ReadAheadFADFunc;
}
}
}

View File

@ -19,11 +19,20 @@ namespace BizHawk.Emulation.Consoles.Sega.Saturn
static Yabause AttachedCore = null;
GCHandle VideoHandle;
DiscSystem.Disc CD;
public Yabause(CoreComm CoreComm)
LibYabause.CDInterface.Init InitH;
LibYabause.CDInterface.DeInit DeInitH;
LibYabause.CDInterface.GetStatus GetStatusH;
LibYabause.CDInterface.ReadTOC ReadTOCH;
LibYabause.CDInterface.ReadSectorFAD ReadSectorFADH;
LibYabause.CDInterface.ReadAheadFAD ReadAheadFADH;
public Yabause(CoreComm CoreComm, DiscSystem.Disc CD)
{
CoreComm.RomStatusDetails = "Yeh";
this.CoreComm = CoreComm;
this.CD = CD;
Init();
}
@ -36,7 +45,15 @@ namespace BizHawk.Emulation.Consoles.Sega.Saturn
}
VideoHandle = GCHandle.Alloc(VideoBuffer, GCHandleType.Pinned);
if (!LibYabause.libyabause_init())
LibYabause.CDInterface CDInt = new LibYabause.CDInterface();
CDInt.InitFunc = InitH = new LibYabause.CDInterface.Init(CD_Init);
CDInt.DeInitFunc = DeInitH = new LibYabause.CDInterface.DeInit(CD_DeInit);
CDInt.GetStatusFunc = GetStatusH = new LibYabause.CDInterface.GetStatus(CD_GetStatus);
CDInt.ReadTOCFunc = ReadTOCH = new LibYabause.CDInterface.ReadTOC(CD_ReadTOC);
CDInt.ReadSectorFADFunc = ReadSectorFADH = new LibYabause.CDInterface.ReadSectorFAD(CD_ReadSectorFAD);
CDInt.ReadAheadFADFunc = ReadAheadFADH = new LibYabause.CDInterface.ReadAheadFAD(CD_ReadAheadFAD);
if (!LibYabause.libyabause_init(ref CDInt))
throw new Exception("libyabause_init() failed!");
LibYabause.libyabause_setvidbuff(VideoHandle.AddrOfPinnedObject());
@ -198,6 +215,114 @@ namespace BizHawk.Emulation.Consoles.Sega.Saturn
}
#endregion
#region CD
/// <summary>
/// init cd functions
/// </summary>
/// <param name="unused"></param>
/// <returns>0 on success, -1 on failure</returns>
int CD_Init(string unused)
{
return 0;
}
/// <summary>
/// deinit cd functions
/// </summary>
void CD_DeInit()
{
}
/// <summary>
/// 0 = cd present, spinning
/// 1 = cd present, not spinning
/// 2 = no cd
/// 3 = tray open
/// </summary>
/// <returns></returns>
int CD_GetStatus()
{
return 0;
}
/// <summary>
/// read all TOC entries
/// </summary>
/// <param name="dest">place to copy to</param>
/// <returns>number of bytes written. should be 408 (99 tracks, 3 specials)</returns>
int CD_ReadTOC(IntPtr dest)
{
// this stuff from yabause's cdbase.c. don't ask me to explain it
var TOC = CD.ReadTOC();
int[] rTOC = new int[102];
var ses = TOC.Sessions[0];
int ntrk = ses.Tracks.Count;
for (int i = 0; i < 99; i++)
{
if (i < ntrk)
{
var trk = ses.Tracks[i];
uint t = (uint)trk.Indexes[1].aba;
switch (trk.TrackType)
{
case DiscSystem.ETrackType.Audio:
t |= 0x01000000;
break;
case DiscSystem.ETrackType.Mode1_2048:
case DiscSystem.ETrackType.Mode1_2352:
case DiscSystem.ETrackType.Mode2_2352:
t |= 0x41000000;
break;
}
rTOC[i] = (int)t;
}
else
{
rTOC[i] = unchecked((int)0xffffffff);
}
}
rTOC[99] = (int)(rTOC[0] & 0xff000000 | 0x010000);
rTOC[100] = (int)(rTOC[ntrk - 1] & 0xff000000 | (uint)(ntrk << 16));
rTOC[101] = (int)(rTOC[ntrk - 1] & 0xff000000 | (uint)(ses.length_aba));
Marshal.Copy(rTOC, 0, dest, 102);
return 408;
}
/// <summary>
/// read a sector, should be 2352 bytes
/// </summary>
/// <param name="FAD"></param>
/// <param name="dest"></param>
/// <returns></returns>
int CD_ReadSectorFAD(int FAD, IntPtr dest)
{
byte[] data = new byte[2352];
try
{
CD.ReadABA_2352(FAD, data, 0);
}
catch (Exception e)
{
Console.WriteLine("CD_ReadSectorFAD: Managed Exception:\n" + e.ToString());
return 0; // failure
}
Marshal.Copy(data, 0, dest, 2352);
return 1; // success
}
/// <summary>
/// hint the next sector, for async loading
/// </summary>
/// <param name="FAD"></param>
void CD_ReadAheadFAD(int FAD)
{
// ignored for now
}
#endregion

View File

@ -1887,7 +1887,7 @@ namespace BizHawk.MultiClient
switch (game.System)
{
case "SAT":
var saturn = new Emulation.Consoles.Sega.Saturn.Yabause(nextComm);
var saturn = new Emulation.Consoles.Sega.Saturn.Yabause(nextComm, disc);
nextEmulator = saturn;
break;

View File

@ -10,6 +10,19 @@ extern "C" {
#include "../yui.h"
}
CDInterface FECD =
{
2,
"FECD",
NULL,
NULL,
NULL,
NULL,
NULL,
NULL,
};
extern "C" SH2Interface_struct *SH2CoreList[] = {
&SH2Interpreter,
&SH2DebugInterpreter,
@ -24,6 +37,7 @@ NULL
extern "C" CDInterface *CDCoreList[] = {
&DummyCD,
&ISOCD,
&FECD,
NULL
};
@ -92,15 +106,22 @@ extern "C" int vdp2width;
/* Tells the yui to exchange front and back video buffers. This may end
up being moved to the Video Core. */
void YuiSwapBuffers(void)
{
{
if (vidbuff)
{
u32 *src = dispbuffer;
u32 *dst = vidbuff;
u8 *src = (u8*)dispbuffer;
u8 *dst = (u8*)vidbuff;
for (int j = 0; j < vdp2height; j++)
for (int i = 0; i < vdp2width; i++)
*dst++ = *src++ | 0xff000000;
{
dst[0] = src[2];
dst[1] = src[1];
dst[2] = src[0];
dst[3] = 0xff;
src += 4;
dst += 4;
}
}
}
@ -132,20 +153,27 @@ extern "C" __declspec(dllexport) void libyabause_deinit()
YabauseDeInit();
}
extern "C" __declspec(dllexport) int libyabause_init()
extern "C" __declspec(dllexport) int libyabause_init(CDInterface *_CD)
{
FECD.DeInit = _CD->DeInit;
FECD.GetStatus = _CD->GetStatus;
FECD.Init = _CD->Init;
FECD.ReadAheadFAD = _CD->ReadAheadFAD;
FECD.ReadSectorFAD = _CD->ReadSectorFAD;
FECD.ReadTOC = _CD->ReadTOC;
yabauseinit_struct yinit;
memset(&yinit, 0, sizeof(yabauseinit_struct));
yinit.percoretype = PERCORE_DUMMY;
yinit.sh2coretype = SH2CORE_INTERPRETER;
yinit.vidcoretype = VIDCORE_SOFT;
yinit.sndcoretype = SNDCORE_DUMMY;
yinit.cdcoretype = CDCORE_ISO; //CDCORE_DUMMY;
yinit.cdcoretype = 2; // CDCORE_ISO; //CDCORE_DUMMY;
yinit.m68kcoretype = M68KCORE_C68K;
yinit.cartpath = CART_NONE;
yinit.regionid = REGION_AUTODETECT;
yinit.biospath = NULL;
yinit.cdpath = "D:\\encodes\\saturnimages\\Castlevania SOTN.iso"; //NULL;
yinit.cdpath = "Saturnus"; //NULL;
yinit.buppath = NULL;
yinit.mpegpath = NULL;
yinit.cartpath = NULL;
@ -154,7 +182,6 @@ extern "C" __declspec(dllexport) int libyabause_init()
if (YabauseInit(&yinit) != 0)
return 0;
return 1;
}