Merge branch 'master' of https://github.com/barry65536/FBAlpha
This commit is contained in:
commit
593201b5ed
|
@ -5,7 +5,6 @@
|
||||||
#include <fstream>
|
#include <fstream>
|
||||||
#include <cstdio>
|
#include <cstdio>
|
||||||
#include <cstring>*/
|
#include <cstring>*/
|
||||||
#include "burnint.h"
|
|
||||||
#include "ide.h"
|
#include "ide.h"
|
||||||
|
|
||||||
#define DEBUG_ATA 0
|
#define DEBUG_ATA 0
|
||||||
|
|
|
@ -2,6 +2,7 @@
|
||||||
#define IDE
|
#define IDE
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
|
#include "burnint.h"
|
||||||
|
|
||||||
namespace ide
|
namespace ide
|
||||||
{
|
{
|
||||||
|
|
|
@ -17417,3 +17417,125 @@ struct BurnDriver BurnDrvKof98mix = {
|
||||||
kof98mixInit, NeoExit, NeoFrame, NeoRender, NeoScan, &NeoRecalcPalette,
|
kof98mixInit, NeoExit, NeoFrame, NeoRender, NeoScan, &NeoRecalcPalette,
|
||||||
0x1000, 304, 224, 4, 3
|
0x1000, 304, 224, 4, 3
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static struct BurnRomInfo kof98pfeRomDesc[] = {
|
||||||
|
{ "242pfe.p1", 0x100000, 0x23876d95, 1 | BRF_ESS | BRF_PRG }, // 1 68K code
|
||||||
|
{ "242pfe.p2", 0x400000, 0xadbaa852, 1 | BRF_ESS | BRF_PRG }, // 1 68K code
|
||||||
|
{ "242pfe.p3", 0x020000, 0x930ea34e, 1 | BRF_ESS | BRF_PRG }, // 1 68K code
|
||||||
|
|
||||||
|
{ "242pfe.s1", 0x020000, 0x7f4dbf23, 2 | BRF_GRA }, // 2 Text layer tiles / TC531000
|
||||||
|
|
||||||
|
{ "242hx73.c1", 0x800000, 0x379654a5, 3 | BRF_GRA }, // 3 Sprite data
|
||||||
|
{ "242hx73.c2", 0x800000, 0x9c71fa3d, 3 | BRF_GRA }, // 4
|
||||||
|
{ "242.c3", 0x800000, 0x22127b4f, 3 | BRF_GRA }, // 5
|
||||||
|
{ "242.c4", 0x800000, 0x0b4fa044, 3 | BRF_GRA }, // 6
|
||||||
|
{ "242.c5", 0x800000, 0x9d10bed3, 3 | BRF_GRA }, // 7
|
||||||
|
{ "242.c6", 0x800000, 0xda07b6a2, 3 | BRF_GRA }, // 8
|
||||||
|
{ "242pfe.c7", 0x800000, 0x02f09b2e, 3 | BRF_GRA }, // 9
|
||||||
|
{ "242pfe.c8", 0x800000, 0xd43ab3e6, 3 | BRF_GRA }, // 10
|
||||||
|
|
||||||
|
{ "242-mg1.m1", 0x040000, 0x4e7a6b1b, 4 | BRF_ESS | BRF_PRG }, // 11 Z80 code
|
||||||
|
|
||||||
|
{ "242.v1", 0x400000, 0xb9ea8051, 5 | BRF_SND }, // 12 Sound data
|
||||||
|
{ "242.v2", 0x400000, 0xcc11106e, 5 | BRF_SND }, // 13
|
||||||
|
{ "242.v3", 0x400000, 0x044ea4e1, 5 | BRF_SND }, // 14
|
||||||
|
{ "242.v4", 0x400000, 0x7985ea30, 5 | BRF_SND }, // 15
|
||||||
|
};
|
||||||
|
|
||||||
|
STDROMPICKEXT(kof98pfe, kof98pfe, neogeo)
|
||||||
|
STD_ROM_FN(kof98pfe)
|
||||||
|
|
||||||
|
static UINT8 *kof98pfeExtraROM;
|
||||||
|
|
||||||
|
static INT32 kof98pfeInit()
|
||||||
|
{
|
||||||
|
INT32 nRet = NeoInit();
|
||||||
|
|
||||||
|
if (nRet == 0) {
|
||||||
|
kof98pfeExtraROM = (UINT8*)BurnMalloc(0x20000);
|
||||||
|
|
||||||
|
if (BurnLoadRom(kof98pfeExtraROM, 2, 1)) return 1;
|
||||||
|
|
||||||
|
kof98pfeExtraROM[0x1af4] = 0x71;
|
||||||
|
kof98pfeExtraROM[0x1af5] = 0x4e;
|
||||||
|
kof98pfeExtraROM[0x1b19] = 0x60;
|
||||||
|
kof98pfeExtraROM[0x1ca3] = 0x60;
|
||||||
|
|
||||||
|
UINT16 *rom = (UINT16*)kof98pfeExtraROM;
|
||||||
|
for (INT32 i = 0; i < 0x20000/2; i++) {
|
||||||
|
if (rom[i] == 0x4e7d) rom[i] = 0x4e71;
|
||||||
|
if (rom[i] == 0x4e7c) rom[i] = 0x4e75;
|
||||||
|
}
|
||||||
|
|
||||||
|
rom = (UINT16*)Neo68KROMActive;
|
||||||
|
|
||||||
|
for (INT32 i = 0; i < 0x100000/2; i++) {
|
||||||
|
if (rom[i] == 0x4e7d) rom[i] = 0x4e71;
|
||||||
|
if (rom[i] == 0x4e7c) rom[i] = 0x4e75;
|
||||||
|
}
|
||||||
|
|
||||||
|
SekOpen(0);
|
||||||
|
SekMapMemory(kof98pfeExtraROM, 0x900000, 0x91ffff, MAP_ROM);
|
||||||
|
SekClose();
|
||||||
|
}
|
||||||
|
|
||||||
|
return nRet;
|
||||||
|
}
|
||||||
|
|
||||||
|
static INT32 kof98pfeExit()
|
||||||
|
{
|
||||||
|
BurnFree (kof98pfeExtraROM);
|
||||||
|
|
||||||
|
return NeoExit();
|
||||||
|
}
|
||||||
|
|
||||||
|
struct BurnDriver BurnDrvkof98pfe = {
|
||||||
|
"kof98pfe", "kof98", "neogeo", NULL, "2017",
|
||||||
|
"Kof'98 (Plus Final Edition)(2017-07-23)(Korean board)\0", NULL, "hack", "Miscellaneous",
|
||||||
|
NULL, NULL, NULL, NULL,
|
||||||
|
BDF_GAME_WORKING | BDF_CLONE | BDF_HACK, 2, HARDWARE_PREFIX_CARTRIDGE | HARDWARE_SNK_NEOGEO, GBF_VSFIGHT, FBF_KOF,
|
||||||
|
NULL, kof98pfeRomInfo, kof98pfeRomName, NULL, NULL, NULL, NULL, neogeoInputInfo, neogeoDIPInfo,
|
||||||
|
kof98pfeInit, kof98pfeExit, NeoFrame, NeoRender, NeoScan, &NeoRecalcPalette,
|
||||||
|
0x1000, 320, 224, 4, 3
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct BurnRomInfo kof10thdRomDesc[] = {
|
||||||
|
{ "363d.p1", 0x800000, 0x30c82f4c, 1 | BRF_ESS | BRF_PRG }, // 1 68K code
|
||||||
|
|
||||||
|
{ "363d.s1", 0x020000, 0x3c757cb1, 2 | BRF_GRA }, // 2 Text layer tiles / TC531000
|
||||||
|
|
||||||
|
{ "kf10-c1a.bin", 0x400000, 0x3bbc0364, 3 | BRF_GRA }, // 3 Sprite data
|
||||||
|
{ "kf10-c2a.bin", 0x400000, 0x91230075, 3 | BRF_GRA }, // 4
|
||||||
|
{ "kf10-c1b.bin", 0x400000, 0xb5abfc28, 3 | BRF_GRA }, // 5
|
||||||
|
{ "kf10-c2b.bin", 0x400000, 0x6cc4c6e1, 3 | BRF_GRA }, // 6
|
||||||
|
{ "kf10-c3a.bin", 0x400000, 0x5b3d4a16, 3 | BRF_GRA }, // 7
|
||||||
|
{ "kf10-c4a.bin", 0x400000, 0xc6f3419b, 3 | BRF_GRA }, // 8
|
||||||
|
{ "kf10-c3b.bin", 0x400000, 0x9d2bba19, 3 | BRF_GRA }, // 9
|
||||||
|
{ "kf10-c4b.bin", 0x400000, 0x5a4050cb, 3 | BRF_GRA }, // 10
|
||||||
|
{ "kf10-c5a.bin", 0x400000, 0xa289d1e1, 3 | BRF_GRA }, // 11
|
||||||
|
{ "kf10-c6a.bin", 0x400000, 0xe6494b5d, 3 | BRF_GRA }, // 12
|
||||||
|
{ "kf10-c5b.bin", 0x400000, 0x404fff02, 3 | BRF_GRA }, // 13
|
||||||
|
{ "kf10-c6b.bin", 0x400000, 0xf2ccfc9e, 3 | BRF_GRA }, // 14
|
||||||
|
{ "kf10-c7a.bin", 0x400000, 0xbe79c5a8, 3 | BRF_GRA }, // 15
|
||||||
|
{ "kf10-c8a.bin", 0x400000, 0xa5952ca4, 3 | BRF_GRA }, // 16
|
||||||
|
{ "kf10-c7b.bin", 0x400000, 0x3fdb3542, 3 | BRF_GRA }, // 17
|
||||||
|
{ "kf10-c8b.bin", 0x400000, 0x661b7a52, 3 | BRF_GRA }, // 18
|
||||||
|
|
||||||
|
{ "kf10-m1.bin", 0x020000, 0xf6fab859, 4 | BRF_ESS | BRF_PRG }, // 19 Z80 code
|
||||||
|
|
||||||
|
{ "kf10-v1.bin", 0x800000, 0x0fc9a58d, 5 | BRF_SND }, // 20 Sound data
|
||||||
|
{ "kf10-v2.bin", 0x800000, 0xb8c475a4, 5 | BRF_SND }, // 21
|
||||||
|
};
|
||||||
|
|
||||||
|
STDROMPICKEXT(kof10thd, kof10thd, neogeo)
|
||||||
|
STD_ROM_FN(kof10thd)
|
||||||
|
|
||||||
|
struct BurnDriver BurnDrvkof10thd = {
|
||||||
|
"kof10thd", "kof2002", "neogeo", NULL, "200?",
|
||||||
|
"Kof 10th Anniversary (The King of Fighters 2002 bootleg / Fully Decrypted)\0", NULL, "hack", "Miscellaneous",
|
||||||
|
NULL, NULL, NULL, NULL,
|
||||||
|
BDF_GAME_WORKING | BDF_CLONE | BDF_HACK, 2, HARDWARE_PREFIX_CARTRIDGE | HARDWARE_SNK_NEOGEO, GBF_VSFIGHT, FBF_KOF,
|
||||||
|
NULL, kof10thdRomInfo, kof10thdRomName, NULL, NULL, NULL, NULL, neogeoInputInfo, neogeoDIPInfo,
|
||||||
|
NeoInit, NeoExit, NeoFrame, NeoRender, NeoScan, &NeoRecalcPalette,
|
||||||
|
0x1000, 304, 224, 4, 3
|
||||||
|
};
|
||||||
|
|
|
@ -1,10 +1,12 @@
|
||||||
// NeoGeo CD-WIP - Jan 25, 2019 - present
|
// NeoGeo CD-WIP - Jan 25, 2019 - present
|
||||||
|
|
||||||
// mit .bin/.cue & .ccd/.img (trurip) unterstutzung (feb.4.2019)
|
// mit .bin/.cue & .ccd/.img (trurip) unterstutzung (feb.4.2019)
|
||||||
// todo:
|
// known issues:
|
||||||
// burner/win32/neocdsel.cpp needs updated to support mode1/2352
|
// Audio Hz rate must be 44100 for proper CDDA speed (auto-handled in fba-ui)
|
||||||
// ssrpg bugs in sfx-audio in cutscene after starting game
|
//
|
||||||
|
// Ninja Commando: glitching "logo" during demo play. This is fixed by
|
||||||
|
// changing renderbyline mode on. A side-effect is that it makes CD-Loading
|
||||||
|
// for other games (karnovr, fatalfury3, etc) very slow. Must investigate.
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* FB Alpha Neo Geo module
|
* FB Alpha Neo Geo module
|
||||||
|
@ -73,8 +75,6 @@
|
||||||
#include "bitswap.h"
|
#include "bitswap.h"
|
||||||
#include "neocdlist.h"
|
#include "neocdlist.h"
|
||||||
|
|
||||||
static INT32 isowav_mode = 0;
|
|
||||||
|
|
||||||
// #undef USE_SPEEDHACKS
|
// #undef USE_SPEEDHACKS
|
||||||
|
|
||||||
// #define LOG_IRQ
|
// #define LOG_IRQ
|
||||||
|
@ -304,8 +304,6 @@ static INT32 NeoCDCommsWordCount = 0;
|
||||||
|
|
||||||
static INT32 NeoCDAssyStatus = 0;
|
static INT32 NeoCDAssyStatus = 0;
|
||||||
|
|
||||||
static INT32 NeoCDTrack = 0;
|
|
||||||
|
|
||||||
static INT32 NeoCDSectorMin = 0;
|
static INT32 NeoCDSectorMin = 0;
|
||||||
static INT32 NeoCDSectorSec = 0;
|
static INT32 NeoCDSectorSec = 0;
|
||||||
static INT32 NeoCDSectorFrm = 0;
|
static INT32 NeoCDSectorFrm = 0;
|
||||||
|
@ -324,9 +322,9 @@ static INT32 NeoCDDMACount = 0;
|
||||||
static INT32 NeoCDDMAMode = 0;
|
static INT32 NeoCDDMAMode = 0;
|
||||||
static INT32 NeoCDVectorSwitch = 0; // 1 ROM(ram), 0 BIOS
|
static INT32 NeoCDVectorSwitch = 0; // 1 ROM(ram), 0 BIOS
|
||||||
|
|
||||||
// hax0r
|
|
||||||
static INT32 nNeoCDMode = 0;
|
static INT32 nNeoCDMode = 0;
|
||||||
static INT32 nff0002 = 0;
|
static INT32 nff0002 = 0;
|
||||||
|
static INT32 nff0004 = 0;
|
||||||
|
|
||||||
|
|
||||||
bool IsNeoGeoCD() {
|
bool IsNeoGeoCD() {
|
||||||
|
@ -668,6 +666,7 @@ static INT32 LoadRoms()
|
||||||
if (!strcmp("kof2k2omg", BurnDrvGetTextA(DRV_NAME))) nYM2610ADPCMASize[nNeoActiveSlot] = 0x1000000;
|
if (!strcmp("kof2k2omg", BurnDrvGetTextA(DRV_NAME))) nYM2610ADPCMASize[nNeoActiveSlot] = 0x1000000;
|
||||||
if (!strcmp("kof2k2omg9b", BurnDrvGetTextA(DRV_NAME))) nYM2610ADPCMASize[nNeoActiveSlot] = 0x1000000;
|
if (!strcmp("kof2k2omg9b", BurnDrvGetTextA(DRV_NAME))) nYM2610ADPCMASize[nNeoActiveSlot] = 0x1000000;
|
||||||
if (!strcmp("kof2k2omg9", BurnDrvGetTextA(DRV_NAME))) nYM2610ADPCMASize[nNeoActiveSlot] = 0x1000000;
|
if (!strcmp("kof2k2omg9", BurnDrvGetTextA(DRV_NAME))) nYM2610ADPCMASize[nNeoActiveSlot] = 0x1000000;
|
||||||
|
if (!strcmp("kof98pfe", BurnDrvGetTextA(DRV_NAME))) nYM2610ADPCMASize[nNeoActiveSlot] = 0x1000000;
|
||||||
|
|
||||||
// bprintf(PRINT_NORMAL, _T("%x\n"), nYM2610ADPCMASize[nNeoActiveSlot]);
|
// bprintf(PRINT_NORMAL, _T("%x\n"), nYM2610ADPCMASize[nNeoActiveSlot]);
|
||||||
|
|
||||||
|
@ -962,7 +961,7 @@ void NeoUpdateVector()
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
// 68K bankswitch for most games without SMA/PVC protection
|
// 68K bankswitch for most games without SMA/PVC protection
|
||||||
|
|
||||||
void __fastcall neogeoWriteByteBankswitch(UINT32 sekAddress, UINT8 byteValue)
|
static void __fastcall neogeoWriteByteBankswitch(UINT32 sekAddress, UINT8 byteValue)
|
||||||
{
|
{
|
||||||
if (sekAddress >= 0x2FFFF0) {
|
if (sekAddress >= 0x2FFFF0) {
|
||||||
|
|
||||||
|
@ -973,7 +972,7 @@ void __fastcall neogeoWriteByteBankswitch(UINT32 sekAddress, UINT8 byteValue)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void __fastcall neogeoWriteWordBankswitch(UINT32 sekAddress, UINT16 wordValue)
|
static void __fastcall neogeoWriteWordBankswitch(UINT32 sekAddress, UINT16 wordValue)
|
||||||
{
|
{
|
||||||
if (sekAddress >= 0x2FFFF0) {
|
if (sekAddress >= 0x2FFFF0) {
|
||||||
|
|
||||||
|
@ -1019,7 +1018,7 @@ static void neogeoFMIRQHandler(INT32, INT32 nStatus)
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
UINT8 __fastcall neogeoReadByteGambling(UINT32 sekAddress)
|
static UINT8 __fastcall neogeoReadByteGambling(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
switch (sekAddress) {
|
switch (sekAddress) {
|
||||||
case 0x280001: {
|
case 0x280001: {
|
||||||
|
@ -1036,7 +1035,7 @@ UINT8 __fastcall neogeoReadByteGambling(UINT32 sekAddress)
|
||||||
return 0xff;
|
return 0xff;
|
||||||
}
|
}
|
||||||
|
|
||||||
UINT16 __fastcall neogeoReadWordGambling(UINT32 sekAddress)
|
static UINT16 __fastcall neogeoReadWordGambling(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
switch (sekAddress) {
|
switch (sekAddress) {
|
||||||
case 0x280000: {
|
case 0x280000: {
|
||||||
|
@ -1053,7 +1052,7 @@ UINT16 __fastcall neogeoReadWordGambling(UINT32 sekAddress)
|
||||||
return 0xffff;
|
return 0xffff;
|
||||||
}
|
}
|
||||||
|
|
||||||
UINT8 __fastcall vliner_timing(UINT32 sekAddress)
|
static UINT8 __fastcall vliner_timing(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
switch (sekAddress) {
|
switch (sekAddress) {
|
||||||
case 0x320000: {
|
case 0x320000: {
|
||||||
|
@ -1439,7 +1438,9 @@ INT32 NeoScan(INT32 nAction, INT32* pnMin)
|
||||||
SekScan(nAction); // Scan 68000 state
|
SekScan(nAction); // Scan 68000 state
|
||||||
ZetScan(nAction); // Scan Z80 state
|
ZetScan(nAction); // Scan Z80 state
|
||||||
|
|
||||||
|
ZetOpen(0);
|
||||||
BurnYM2610Scan(nAction, pnMin);
|
BurnYM2610Scan(nAction, pnMin);
|
||||||
|
ZetClose();
|
||||||
|
|
||||||
if (nNeoSystemType & NEO_SYS_MVS) {
|
if (nNeoSystemType & NEO_SYS_MVS) {
|
||||||
uPD4990AScan(nAction, pnMin);
|
uPD4990AScan(nAction, pnMin);
|
||||||
|
@ -1501,7 +1502,6 @@ INT32 NeoScan(INT32 nAction, INT32* pnMin)
|
||||||
// BurnGameFeedback(sizeof(nLED), nLED);
|
// BurnGameFeedback(sizeof(nLED), nLED);
|
||||||
|
|
||||||
if (nNeoSystemType & NEO_SYS_CD) {
|
if (nNeoSystemType & NEO_SYS_CD) {
|
||||||
//xxxxxxxxxxxxxxxx
|
|
||||||
SCAN_VAR(bNeoCDIRQEnabled);
|
SCAN_VAR(bNeoCDIRQEnabled);
|
||||||
SCAN_VAR(nNeoCDIRQVector);
|
SCAN_VAR(nNeoCDIRQVector);
|
||||||
SCAN_VAR(nNeoCDIRQVectorAck);
|
SCAN_VAR(nNeoCDIRQVectorAck);
|
||||||
|
@ -1528,8 +1528,6 @@ INT32 NeoScan(INT32 nAction, INT32* pnMin)
|
||||||
|
|
||||||
SCAN_VAR(NeoCDAssyStatus);
|
SCAN_VAR(NeoCDAssyStatus);
|
||||||
|
|
||||||
SCAN_VAR(NeoCDTrack);
|
|
||||||
|
|
||||||
SCAN_VAR(NeoCDSectorMin);
|
SCAN_VAR(NeoCDSectorMin);
|
||||||
SCAN_VAR(NeoCDSectorSec);
|
SCAN_VAR(NeoCDSectorSec);
|
||||||
SCAN_VAR(NeoCDSectorFrm);
|
SCAN_VAR(NeoCDSectorFrm);
|
||||||
|
@ -1551,6 +1549,8 @@ INT32 NeoScan(INT32 nAction, INT32* pnMin)
|
||||||
|
|
||||||
SCAN_VAR(nNeoCDMode);
|
SCAN_VAR(nNeoCDMode);
|
||||||
SCAN_VAR(nff0002);
|
SCAN_VAR(nff0002);
|
||||||
|
SCAN_VAR(nff0004);
|
||||||
|
|
||||||
CDEmuScan(nAction, pnMin);
|
CDEmuScan(nAction, pnMin);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1622,7 +1622,7 @@ INT32 NeoScan(INT32 nAction, INT32* pnMin)
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
// Z80 handlers
|
// Z80 handlers
|
||||||
|
|
||||||
UINT8 __fastcall neogeoZ80In(UINT16 nAddress)
|
static UINT8 __fastcall neogeoZ80In(UINT16 nAddress)
|
||||||
{
|
{
|
||||||
switch (nAddress & 0xFF) {
|
switch (nAddress & 0xFF) {
|
||||||
case 0x00: // Read sound command
|
case 0x00: // Read sound command
|
||||||
|
@ -1665,7 +1665,7 @@ UINT8 __fastcall neogeoZ80In(UINT16 nAddress)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
UINT8 __fastcall neogeoZ80InCD(UINT16 nAddress)
|
static UINT8 __fastcall neogeoZ80InCD(UINT16 nAddress)
|
||||||
{
|
{
|
||||||
switch (nAddress & 0xFF) {
|
switch (nAddress & 0xFF) {
|
||||||
case 0x00: // Read sound command
|
case 0x00: // Read sound command
|
||||||
|
@ -1698,7 +1698,7 @@ UINT8 __fastcall neogeoZ80InCD(UINT16 nAddress)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void __fastcall neogeoZ80Out(UINT16 nAddress, UINT8 nValue)
|
static void __fastcall neogeoZ80Out(UINT16 nAddress, UINT8 nValue)
|
||||||
{
|
{
|
||||||
switch (nAddress & 0x0FF) {
|
switch (nAddress & 0x0FF) {
|
||||||
case 0x00:
|
case 0x00:
|
||||||
|
@ -1740,8 +1740,10 @@ void __fastcall neogeoZ80Out(UINT16 nAddress, UINT8 nValue)
|
||||||
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x80:
|
case 0x80: // NOP
|
||||||
bprintf(PRINT_ERROR, _T(" - Z80 port 0x%04X -> 0x%02X.\n"), nAddress, nValue);
|
case 0xc0:
|
||||||
|
case 0xc1:
|
||||||
|
case 0xc2:
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default: {
|
default: {
|
||||||
|
@ -1753,7 +1755,7 @@ void __fastcall neogeoZ80Out(UINT16 nAddress, UINT8 nValue)
|
||||||
// -----------------------------------------------------------------------------
|
// -----------------------------------------------------------------------------
|
||||||
// 68K handlers
|
// 68K handlers
|
||||||
|
|
||||||
INT32 __fastcall NeoCDIRQCallback(INT32 /* nIRQ */)
|
static INT32 __fastcall NeoCDIRQCallback(INT32 /* nIRQ */)
|
||||||
{
|
{
|
||||||
// bprintf(PRINT_NORMAL, _T(" - IRQ Callback %i %2X.\n"), nIRQ, nNeoCDIRQVector);
|
// bprintf(PRINT_NORMAL, _T(" - IRQ Callback %i %2X.\n"), nIRQ, nNeoCDIRQVector);
|
||||||
if (nNeoCDIRQVectorAck) {
|
if (nNeoCDIRQVectorAck) {
|
||||||
|
@ -1795,7 +1797,6 @@ static inline void NeoCDIRQUpdate(UINT8 byteValue)
|
||||||
{
|
{
|
||||||
nIRQAcknowledge |= (byteValue & 0x38);
|
nIRQAcknowledge |= (byteValue & 0x38);
|
||||||
|
|
||||||
if (!bNeoCDIRQEnabled) return;
|
|
||||||
// bprintf(PRINT_NORMAL, _T(" - IRQ Ack -> %02X (CD, at line %3i).\n"), nIRQAcknowledge, SekCurrentScanline());
|
// bprintf(PRINT_NORMAL, _T(" - IRQ Ack -> %02X (CD, at line %3i).\n"), nIRQAcknowledge, SekCurrentScanline());
|
||||||
|
|
||||||
if ((nIRQAcknowledge & 0x3F) == 0x3F) {
|
if ((nIRQAcknowledge & 0x3F) == 0x3F) {
|
||||||
|
@ -1805,6 +1806,9 @@ static inline void NeoCDIRQUpdate(UINT8 byteValue)
|
||||||
NeoIRQUpdate(0);
|
NeoIRQUpdate(0);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!bNeoCDIRQEnabled) return;
|
||||||
|
|
||||||
if ((nIRQAcknowledge & 0x08) == 0) {
|
if ((nIRQAcknowledge & 0x08) == 0) {
|
||||||
nNeoCDIRQVector = 0x17;
|
nNeoCDIRQVector = 0x17;
|
||||||
nNeoCDIRQVectorAck = 1;
|
nNeoCDIRQVectorAck = 1;
|
||||||
|
@ -1887,8 +1891,11 @@ static UINT8 ReadInput3(INT32 nOffset)
|
||||||
return ~0;
|
return ~0;
|
||||||
}
|
}
|
||||||
|
|
||||||
UINT8 __fastcall neogeoReadByte(UINT32 sekAddress)
|
static UINT8 __fastcall neogeoReadByte(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
|
if (sekAddress >= 0x200000 && sekAddress <= 0x2fffff)
|
||||||
|
return ~0; // data from open bus should be read here
|
||||||
|
|
||||||
switch (sekAddress & 0xFE0000) {
|
switch (sekAddress & 0xFE0000) {
|
||||||
case 0x300000:
|
case 0x300000:
|
||||||
return ReadInput1(sekAddress & 0xFF);
|
return ReadInput1(sekAddress & 0xFF);
|
||||||
|
@ -1938,8 +1945,11 @@ UINT8 __fastcall neogeoReadByte(UINT32 sekAddress)
|
||||||
return ~0;
|
return ~0;
|
||||||
}
|
}
|
||||||
|
|
||||||
UINT16 __fastcall neogeoReadWord(UINT32 sekAddress)
|
static UINT16 __fastcall neogeoReadWord(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
|
if (sekAddress >= 0x200000 && sekAddress <= 0x2fffff)
|
||||||
|
return ~0; // data from open bus should be read here
|
||||||
|
|
||||||
switch (sekAddress & 0xFE0000) {
|
switch (sekAddress & 0xFE0000) {
|
||||||
case 0x300000:
|
case 0x300000:
|
||||||
return (ReadInput1(sekAddress & 0xFE) << 8) | ReadInput1((sekAddress & 0xFE) | 1);
|
return (ReadInput1(sekAddress & 0xFE) << 8) | ReadInput1((sekAddress & 0xFE) | 1);
|
||||||
|
@ -2152,7 +2162,7 @@ static void WriteIO2(INT32 nOffset, UINT8 /*byteValue*/)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
void __fastcall neogeoWriteByte(UINT32 sekAddress, UINT8 byteValue)
|
static void __fastcall neogeoWriteByte(UINT32 sekAddress, UINT8 byteValue)
|
||||||
{
|
{
|
||||||
switch (sekAddress & 0xFF0000) {
|
switch (sekAddress & 0xFF0000) {
|
||||||
case 0x300000:
|
case 0x300000:
|
||||||
|
@ -2198,7 +2208,7 @@ void __fastcall neogeoWriteWord(UINT32 sekAddress, UINT16 wordValue)
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
// Video controller reads
|
// Video controller reads
|
||||||
|
|
||||||
UINT16 __fastcall neogeoReadWordVideo(UINT32 sekAddress)
|
static UINT16 __fastcall neogeoReadWordVideo(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
switch (sekAddress & 6) {
|
switch (sekAddress & 6) {
|
||||||
case 0x00:
|
case 0x00:
|
||||||
|
@ -2223,7 +2233,7 @@ UINT16 __fastcall neogeoReadWordVideo(UINT32 sekAddress)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
UINT8 __fastcall neogeoReadByteVideo(UINT32 sekAddress)
|
static UINT8 __fastcall neogeoReadByteVideo(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
if (sekAddress & 1) {
|
if (sekAddress & 1) {
|
||||||
return 0x0FF;
|
return 0x0FF;
|
||||||
|
@ -2232,7 +2242,7 @@ UINT8 __fastcall neogeoReadByteVideo(UINT32 sekAddress)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void __fastcall neogeoWriteWordVideo(UINT32 sekAddress, UINT16 wordValue)
|
static void __fastcall neogeoWriteWordVideo(UINT32 sekAddress, UINT16 wordValue)
|
||||||
{
|
{
|
||||||
// if (sekAddress >= 0x3C0010)
|
// if (sekAddress >= 0x3C0010)
|
||||||
// bprintf(PRINT_NORMAL, _T(" - Attempt to write word 0x%06X -> 0x%04X\n"), sekAddress, wordValue);
|
// bprintf(PRINT_NORMAL, _T(" - Attempt to write word 0x%06X -> 0x%04X\n"), sekAddress, wordValue);
|
||||||
|
@ -2350,7 +2360,7 @@ void __fastcall neogeoWriteWordVideo(UINT32 sekAddress, UINT16 wordValue)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void __fastcall neogeoWriteByteVideo(UINT32 sekAddress, UINT8 byteValue)
|
static void __fastcall neogeoWriteByteVideo(UINT32 sekAddress, UINT8 byteValue)
|
||||||
{
|
{
|
||||||
// bprintf(PRINT_NORMAL, _T(" - Attempt to write byte 0x%06X -> 0x%02X\n"), sekAddress, byteValue);
|
// bprintf(PRINT_NORMAL, _T(" - Attempt to write byte 0x%06X -> 0x%02X\n"), sekAddress, byteValue);
|
||||||
|
|
||||||
|
@ -2374,7 +2384,7 @@ void __fastcall neogeoWriteByteVideo(UINT32 sekAddress, UINT8 byteValue)
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
// Backup RAM on MVS hardware
|
// Backup RAM on MVS hardware
|
||||||
|
|
||||||
void __fastcall neogeoWriteByteSRAM(UINT32 sekAddress, UINT8 byteValue)
|
static void __fastcall neogeoWriteByteSRAM(UINT32 sekAddress, UINT8 byteValue)
|
||||||
{
|
{
|
||||||
sekAddress &= 0xFFFF;
|
sekAddress &= 0xFFFF;
|
||||||
|
|
||||||
|
@ -2383,7 +2393,7 @@ void __fastcall neogeoWriteByteSRAM(UINT32 sekAddress, UINT8 byteValue)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void __fastcall neogeoWriteWordSRAM(UINT32 sekAddress, UINT16 wordValue)
|
static void __fastcall neogeoWriteWordSRAM(UINT32 sekAddress, UINT16 wordValue)
|
||||||
{
|
{
|
||||||
sekAddress &= 0xFFFF;
|
sekAddress &= 0xFFFF;
|
||||||
|
|
||||||
|
@ -2394,7 +2404,7 @@ void __fastcall neogeoWriteWordSRAM(UINT32 sekAddress, UINT16 wordValue)
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
UINT8 __fastcall neogeoReadByteMemoryCard(UINT32 sekAddress)
|
static UINT8 __fastcall neogeoReadByteMemoryCard(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
// if (sekAddress < 0x800100)
|
// if (sekAddress < 0x800100)
|
||||||
// bprintf(PRINT_NORMAL, _T(" - Memcard 0x%04X read (PC: 0x%06X).\n"), sekAddress & 0x7FFF, SekGetPC(-1));
|
// bprintf(PRINT_NORMAL, _T(" - Memcard 0x%04X read (PC: 0x%06X).\n"), sekAddress & 0x7FFF, SekGetPC(-1));
|
||||||
|
@ -2408,7 +2418,7 @@ UINT8 __fastcall neogeoReadByteMemoryCard(UINT32 sekAddress)
|
||||||
return 0xFF;
|
return 0xFF;
|
||||||
}
|
}
|
||||||
|
|
||||||
void __fastcall neogeoWriteByteMemoryCard(UINT32 sekAddress, UINT8 byteValue)
|
static void __fastcall neogeoWriteByteMemoryCard(UINT32 sekAddress, UINT8 byteValue)
|
||||||
{
|
{
|
||||||
// if (sekAddress < 0x800100)
|
// if (sekAddress < 0x800100)
|
||||||
// bprintf(PRINT_NORMAL, _T(" - Memcard 0x%04X -> 0x%02X (PC: 0x%06X).\n"), sekAddress & 0x7FFF, byteValue, SekGetPC(-1));
|
// bprintf(PRINT_NORMAL, _T(" - Memcard 0x%04X -> 0x%02X (PC: 0x%06X).\n"), sekAddress & 0x7FFF, byteValue, SekGetPC(-1));
|
||||||
|
@ -2420,7 +2430,7 @@ void __fastcall neogeoWriteByteMemoryCard(UINT32 sekAddress, UINT8 byteValue)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
UINT8 __fastcall neoCDReadByteMemoryCard(UINT32 sekAddress)
|
static UINT8 __fastcall neoCDReadByteMemoryCard(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
sekAddress &= 0x01FFFF;
|
sekAddress &= 0x01FFFF;
|
||||||
if (sekAddress < 0x4000 && sekAddress & 1) {
|
if (sekAddress < 0x4000 && sekAddress & 1) {
|
||||||
|
@ -2430,7 +2440,7 @@ UINT8 __fastcall neoCDReadByteMemoryCard(UINT32 sekAddress)
|
||||||
return 0xFF;
|
return 0xFF;
|
||||||
}
|
}
|
||||||
|
|
||||||
void __fastcall neoCDWriteByteMemoryCard(UINT32 sekAddress, UINT8 byteValue)
|
static void __fastcall neoCDWriteByteMemoryCard(UINT32 sekAddress, UINT8 byteValue)
|
||||||
{
|
{
|
||||||
sekAddress &= 0x01FFFF;
|
sekAddress &= 0x01FFFF;
|
||||||
if (sekAddress < 0x4000 && sekAddress & 1) {
|
if (sekAddress < 0x4000 && sekAddress & 1) {
|
||||||
|
@ -2491,6 +2501,7 @@ static void NeoCDCommsReset()
|
||||||
bNeoCDLoadSector = false;
|
bNeoCDLoadSector = false;
|
||||||
|
|
||||||
nNeoCDMode = 0;
|
nNeoCDMode = 0;
|
||||||
|
NeoCDSectorLBA = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void LC8951UpdateHeader()
|
static void LC8951UpdateHeader()
|
||||||
|
@ -2509,18 +2520,11 @@ static void LC8951UpdateHeader()
|
||||||
} else {
|
} else {
|
||||||
|
|
||||||
// HEAD registers have header
|
// HEAD registers have header
|
||||||
if (isowav_mode) {
|
|
||||||
LC8951RegistersR[4] = ((NeoCDSectorMin / 10) << 4) | (NeoCDSectorMin % 10); // HEAD0
|
|
||||||
LC8951RegistersR[5] = ((NeoCDSectorSec / 10) << 4) | (NeoCDSectorSec % 10); // HEAD1
|
|
||||||
LC8951RegistersR[6] = ((NeoCDSectorFrm / 10) << 4) | (NeoCDSectorFrm % 10); // HEAD2
|
|
||||||
LC8951RegistersR[7] = 1; // HEAD3
|
|
||||||
} else {
|
|
||||||
LC8951RegistersR[4] = NeoCDSectorData[12]; // HEAD0
|
LC8951RegistersR[4] = NeoCDSectorData[12]; // HEAD0
|
||||||
LC8951RegistersR[5] = NeoCDSectorData[13]; // HEAD1
|
LC8951RegistersR[5] = NeoCDSectorData[13]; // HEAD1
|
||||||
LC8951RegistersR[6] = NeoCDSectorData[14]; // HEAD2
|
LC8951RegistersR[6] = NeoCDSectorData[14]; // HEAD2
|
||||||
LC8951RegistersR[7] = NeoCDSectorData[15]; // HEAD3
|
LC8951RegistersR[7] = NeoCDSectorData[15]; // HEAD3
|
||||||
}
|
}
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static char* LC8951InitTransfer()
|
static char* LC8951InitTransfer()
|
||||||
|
@ -2538,11 +2542,7 @@ static char* LC8951InitTransfer()
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isowav_mode) {
|
|
||||||
return NeoCDSectorData + ((LC8951RegistersW[5] << 8) | LC8951RegistersW[4]);
|
|
||||||
} else {
|
|
||||||
return NeoCDSectorData + 12 + ((LC8951RegistersW[5] << 8) | LC8951RegistersW[4]);
|
return NeoCDSectorData + 12 + ((LC8951RegistersW[5] << 8) | LC8951RegistersW[4]);
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void LC8951EndTransfer()
|
static void LC8951EndTransfer()
|
||||||
|
@ -2563,6 +2563,7 @@ static void LC8951EndTransfer()
|
||||||
|
|
||||||
static void LC8951Reset()
|
static void LC8951Reset()
|
||||||
{
|
{
|
||||||
|
nLC8951Register = 0;
|
||||||
memset(LC8951RegistersR, 0, sizeof(LC8951RegistersR));
|
memset(LC8951RegistersR, 0, sizeof(LC8951RegistersR));
|
||||||
memset(LC8951RegistersW, 0, sizeof(LC8951RegistersW));
|
memset(LC8951RegistersW, 0, sizeof(LC8951RegistersW));
|
||||||
|
|
||||||
|
@ -2575,10 +2576,6 @@ static void LC8951Reset()
|
||||||
LC8951UpdateHeader();
|
LC8951UpdateHeader();
|
||||||
}
|
}
|
||||||
|
|
||||||
// for NeoGeo CD (WAV playback)
|
|
||||||
//void wav_exit();
|
|
||||||
//void wav_pause(bool bResume);
|
|
||||||
|
|
||||||
static void NeoCDProcessCommand()
|
static void NeoCDProcessCommand()
|
||||||
{
|
{
|
||||||
memset(NeoCDCommsStatusFIFO, 0, sizeof(NeoCDCommsStatusFIFO));
|
memset(NeoCDCommsStatusFIFO, 0, sizeof(NeoCDCommsStatusFIFO));
|
||||||
|
@ -2605,18 +2602,6 @@ static void NeoCDProcessCommand()
|
||||||
case 0: {
|
case 0: {
|
||||||
UINT8* ChannelData = CDEmuReadQChannel();
|
UINT8* ChannelData = CDEmuReadQChannel();
|
||||||
|
|
||||||
if (isowav_mode) {
|
|
||||||
NeoCDCommsStatusFIFO[2] = ChannelData[1] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[3] = ChannelData[1] % 10;
|
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[4] = ChannelData[2] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[5] = ChannelData[2] % 10;
|
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[6] = ChannelData[3] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[7] = ChannelData[3] % 10;
|
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[8] = ChannelData[7];
|
|
||||||
} else {
|
|
||||||
NeoCDCommsStatusFIFO[2] = ChannelData[1] >> 4;
|
NeoCDCommsStatusFIFO[2] = ChannelData[1] >> 4;
|
||||||
NeoCDCommsStatusFIFO[3] = ChannelData[1] & 0x0F;
|
NeoCDCommsStatusFIFO[3] = ChannelData[1] & 0x0F;
|
||||||
|
|
||||||
|
@ -2626,8 +2611,7 @@ static void NeoCDProcessCommand()
|
||||||
NeoCDCommsStatusFIFO[6] = ChannelData[3] >> 4;
|
NeoCDCommsStatusFIFO[6] = ChannelData[3] >> 4;
|
||||||
NeoCDCommsStatusFIFO[7] = ChannelData[3] & 0x0F;
|
NeoCDCommsStatusFIFO[7] = ChannelData[3] & 0x0F;
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[8] = ChannelData[7];
|
NeoCDCommsStatusFIFO[8] = ChannelData[7] >> 4;
|
||||||
}
|
|
||||||
|
|
||||||
// bprintf(PRINT_ERROR, _T(" %02i %02i:%02i:%02i %02i:%02i:%02i %02i\n"), ChannelData[0], ChannelData[1], ChannelData[2], ChannelData[3], ChannelData[4], ChannelData[5], ChannelData[6], ChannelData[7]);
|
// bprintf(PRINT_ERROR, _T(" %02i %02i:%02i:%02i %02i:%02i:%02i %02i\n"), ChannelData[0], ChannelData[1], ChannelData[2], ChannelData[3], ChannelData[4], ChannelData[5], ChannelData[6], ChannelData[7]);
|
||||||
|
|
||||||
|
@ -2636,18 +2620,6 @@ static void NeoCDProcessCommand()
|
||||||
case 1: {
|
case 1: {
|
||||||
UINT8* ChannelData = CDEmuReadQChannel();
|
UINT8* ChannelData = CDEmuReadQChannel();
|
||||||
|
|
||||||
if (isowav_mode) {
|
|
||||||
NeoCDCommsStatusFIFO[2] = ChannelData[4] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[3] = ChannelData[4] % 10;
|
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[4] = ChannelData[5] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[5] = ChannelData[5] % 10;
|
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[6] = ChannelData[6] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[7] = ChannelData[6] % 10;
|
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[8] = ChannelData[7];
|
|
||||||
} else {
|
|
||||||
NeoCDCommsStatusFIFO[2] = ChannelData[4] >> 4;
|
NeoCDCommsStatusFIFO[2] = ChannelData[4] >> 4;
|
||||||
NeoCDCommsStatusFIFO[3] = ChannelData[4] & 0x0F;
|
NeoCDCommsStatusFIFO[3] = ChannelData[4] & 0x0F;
|
||||||
|
|
||||||
|
@ -2657,42 +2629,27 @@ static void NeoCDProcessCommand()
|
||||||
NeoCDCommsStatusFIFO[6] = ChannelData[6] >> 4;
|
NeoCDCommsStatusFIFO[6] = ChannelData[6] >> 4;
|
||||||
NeoCDCommsStatusFIFO[7] = ChannelData[6] & 0x0F;
|
NeoCDCommsStatusFIFO[7] = ChannelData[6] & 0x0F;
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[8] = ChannelData[7];
|
NeoCDCommsStatusFIFO[8] = ChannelData[7] >> 4;
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case 2: {
|
case 2: {
|
||||||
|
|
||||||
UINT8* ChannelData = CDEmuReadQChannel();
|
UINT8* ChannelData = CDEmuReadQChannel();
|
||||||
|
|
||||||
if (isowav_mode) {
|
|
||||||
NeoCDCommsStatusFIFO[2] = ChannelData[0] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[3] = ChannelData[0] % 10;
|
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[8] = ChannelData[7];
|
|
||||||
} else {
|
|
||||||
NeoCDCommsStatusFIFO[2] = ChannelData[0] >> 4;
|
NeoCDCommsStatusFIFO[2] = ChannelData[0] >> 4;
|
||||||
NeoCDCommsStatusFIFO[3] = ChannelData[0] & 0x0F;
|
NeoCDCommsStatusFIFO[3] = ChannelData[0] & 0x0F;
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[8] = ChannelData[7];
|
UINT8* TOCEntry = CDEmuReadTOC(CDEmuTOC_FIRSTINDEX);
|
||||||
}
|
NeoCDCommsStatusFIFO[4] = TOCEntry[0] >> 4;
|
||||||
|
NeoCDCommsStatusFIFO[5] = TOCEntry[0] & 0x0F;
|
||||||
|
|
||||||
|
NeoCDCommsStatusFIFO[8] = ChannelData[7] >> 4;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case 3: {
|
case 3: {
|
||||||
UINT8* TOCEntry = CDEmuReadTOC(-2);
|
UINT8* TOCEntry = CDEmuReadTOC(CDEmuTOC_LASTMSF);
|
||||||
|
|
||||||
if (isowav_mode) {
|
|
||||||
NeoCDCommsStatusFIFO[2] = TOCEntry[0] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[3] = TOCEntry[0] % 10;
|
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[4] = TOCEntry[1] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[5] = TOCEntry[1] % 10;
|
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[6] = TOCEntry[2] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[7] = TOCEntry[2] % 10;
|
|
||||||
} else {
|
|
||||||
NeoCDCommsStatusFIFO[2] = TOCEntry[0] >> 4;
|
NeoCDCommsStatusFIFO[2] = TOCEntry[0] >> 4;
|
||||||
NeoCDCommsStatusFIFO[3] = TOCEntry[0] & 0x0F;
|
NeoCDCommsStatusFIFO[3] = TOCEntry[0] & 0x0F;
|
||||||
|
|
||||||
|
@ -2701,44 +2658,25 @@ static void NeoCDProcessCommand()
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[6] = TOCEntry[2] >> 4;
|
NeoCDCommsStatusFIFO[6] = TOCEntry[2] >> 4;
|
||||||
NeoCDCommsStatusFIFO[7] = TOCEntry[2] & 0x0F;
|
NeoCDCommsStatusFIFO[7] = TOCEntry[2] & 0x0F;
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case 4: {
|
case 4: {
|
||||||
UINT8* TOCEntry = CDEmuReadTOC(-1);
|
UINT8* TOCEntry = CDEmuReadTOC(CDEmuTOC_FIRSTLAST);
|
||||||
|
|
||||||
if (isowav_mode) {
|
|
||||||
NeoCDCommsStatusFIFO[2] = TOCEntry[0] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[3] = TOCEntry[0] % 10;
|
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[4] = TOCEntry[1] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[5] = TOCEntry[1] % 10;
|
|
||||||
} else {
|
|
||||||
NeoCDCommsStatusFIFO[2] = TOCEntry[0] > 4;
|
NeoCDCommsStatusFIFO[2] = TOCEntry[0] > 4;
|
||||||
NeoCDCommsStatusFIFO[3] = TOCEntry[0] & 0x0F;
|
NeoCDCommsStatusFIFO[3] = TOCEntry[0] & 0x0F;
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[4] = TOCEntry[1] >> 4;
|
NeoCDCommsStatusFIFO[4] = TOCEntry[1] >> 4;
|
||||||
NeoCDCommsStatusFIFO[5] = TOCEntry[1] & 0x0F;
|
NeoCDCommsStatusFIFO[5] = TOCEntry[1] & 0x0F;
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case 5: {
|
case 5: {
|
||||||
NeoCDTrack = (NeoCDCommsCommandFIFO[4] << 4) | NeoCDCommsCommandFIFO[5];
|
INT32 NeoCDTrack = (NeoCDCommsCommandFIFO[4] << 4) | NeoCDCommsCommandFIFO[5];
|
||||||
|
|
||||||
UINT8* TOCEntry = CDEmuReadTOC(NeoCDTrack);
|
UINT8* TOCEntry = CDEmuReadTOC(NeoCDTrack);
|
||||||
|
|
||||||
if (isowav_mode) {
|
|
||||||
NeoCDCommsStatusFIFO[2] = TOCEntry[0] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[3] = TOCEntry[0] % 10;
|
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[4] = TOCEntry[1] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[5] = TOCEntry[1] % 10;
|
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[6] = TOCEntry[2] / 10;
|
|
||||||
NeoCDCommsStatusFIFO[7] = TOCEntry[2] % 10;
|
|
||||||
} else {
|
|
||||||
NeoCDCommsStatusFIFO[2] = TOCEntry[0] >> 4;
|
NeoCDCommsStatusFIFO[2] = TOCEntry[0] >> 4;
|
||||||
NeoCDCommsStatusFIFO[3] = TOCEntry[0] & 0x0F;
|
NeoCDCommsStatusFIFO[3] = TOCEntry[0] & 0x0F;
|
||||||
|
|
||||||
|
@ -2747,36 +2685,29 @@ static void NeoCDProcessCommand()
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[6] = TOCEntry[2] >> 4;
|
NeoCDCommsStatusFIFO[6] = TOCEntry[2] >> 4;
|
||||||
NeoCDCommsStatusFIFO[7] = TOCEntry[2] & 0x0F;
|
NeoCDCommsStatusFIFO[7] = TOCEntry[2] & 0x0F;
|
||||||
}
|
|
||||||
|
|
||||||
// bit 3 of the 1st minutes digit indicates a data track
|
// bit 3 of the 1st minutes digit indicates a data track
|
||||||
if (TOCEntry[3] & 4) {
|
if (TOCEntry[3] & 4) {
|
||||||
NeoCDCommsStatusFIFO[6] |= 8;
|
NeoCDCommsStatusFIFO[6] |= 8;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isowav_mode) {
|
|
||||||
NeoCDCommsStatusFIFO[8] = NeoCDTrack % 10;
|
|
||||||
} else {
|
|
||||||
NeoCDCommsStatusFIFO[8] = NeoCDTrack & 0x0F;
|
NeoCDCommsStatusFIFO[8] = NeoCDTrack & 0x0F;
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
case 6: {
|
case 6: {
|
||||||
|
|
||||||
UINT8* ChannelData = CDEmuReadQChannel();
|
UINT8* ChannelData = CDEmuReadQChannel();
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[8] = ChannelData[7];
|
NeoCDCommsStatusFIFO[8] = ChannelData[7] >> 4;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
case 7: {
|
case 7: {
|
||||||
|
|
||||||
// must be 02, 0E, 0F, or 05
|
// must be 02, 0E, 0F, or 05
|
||||||
NeoCDCommsStatusFIFO[2] = 0;
|
NeoCDCommsStatusFIFO[2] = 0;
|
||||||
NeoCDCommsStatusFIFO[3] = (isowav_mode) ? 5 : NeoCDAssyStatus;
|
NeoCDCommsStatusFIFO[3] = NeoCDAssyStatus;
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[4] = 0;
|
NeoCDCommsStatusFIFO[4] = 0;
|
||||||
NeoCDCommsStatusFIFO[5] = 0;
|
NeoCDCommsStatusFIFO[5] = 0;
|
||||||
|
@ -2803,9 +2734,6 @@ static void NeoCDProcessCommand()
|
||||||
NeoCDSectorLBA += NeoCDCommsCommandFIFO[6] * (10 );
|
NeoCDSectorLBA += NeoCDCommsCommandFIFO[6] * (10 );
|
||||||
NeoCDSectorLBA += NeoCDCommsCommandFIFO[7] * ( 1 );
|
NeoCDSectorLBA += NeoCDCommsCommandFIFO[7] * ( 1 );
|
||||||
|
|
||||||
if (isowav_mode)
|
|
||||||
NeoCDSectorLBA -= CD_FRAMES_PREGAP;
|
|
||||||
|
|
||||||
CDEmuStartRead();
|
CDEmuStartRead();
|
||||||
// LC8951RegistersR[1] |= 0x20;
|
// LC8951RegistersR[1] |= 0x20;
|
||||||
} else {
|
} else {
|
||||||
|
@ -2814,12 +2742,8 @@ static void NeoCDProcessCommand()
|
||||||
bprintf(PRINT_ERROR, _T("*** Switching CD mode to audio while in CD-ROM mode!(PC: 0x%06X)\n"), SekGetPC(-1));
|
bprintf(PRINT_ERROR, _T("*** Switching CD mode to audio while in CD-ROM mode!(PC: 0x%06X)\n"), SekGetPC(-1));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isowav_mode) {
|
|
||||||
CDEmuPlay((NeoCDCommsCommandFIFO[2] * 10) + NeoCDCommsCommandFIFO[3], (NeoCDCommsCommandFIFO[4] * 10) + NeoCDCommsCommandFIFO[5], (NeoCDCommsCommandFIFO[6] * 10) + NeoCDCommsCommandFIFO[7]);
|
|
||||||
} else {
|
|
||||||
CDEmuPlay((NeoCDCommsCommandFIFO[2] * 16) + NeoCDCommsCommandFIFO[3], (NeoCDCommsCommandFIFO[4] * 16) + NeoCDCommsCommandFIFO[5], (NeoCDCommsCommandFIFO[6] * 16) + NeoCDCommsCommandFIFO[7]);
|
CDEmuPlay((NeoCDCommsCommandFIFO[2] * 16) + NeoCDCommsCommandFIFO[3], (NeoCDCommsCommandFIFO[4] * 16) + NeoCDCommsCommandFIFO[5], (NeoCDCommsCommandFIFO[6] * 16) + NeoCDCommsCommandFIFO[7]);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
NeoCDAssyStatus = 1;
|
NeoCDAssyStatus = 1;
|
||||||
bNeoCDLoadSector = true;
|
bNeoCDLoadSector = true;
|
||||||
|
@ -2841,14 +2765,12 @@ static void NeoCDProcessCommand()
|
||||||
NeoCDAssyStatus = 4;
|
NeoCDAssyStatus = 4;
|
||||||
bNeoCDLoadSector = false;
|
bNeoCDLoadSector = false;
|
||||||
CDEmuPause();
|
CDEmuPause();
|
||||||
//if (isowav_mode) wav_pause(0);
|
|
||||||
break;
|
break;
|
||||||
case 7:
|
case 7:
|
||||||
// bprintf(PRINT_ERROR, _T(" CD comms received command %i\n"), NeoCDCommsCommandFIFO[0]);
|
// bprintf(PRINT_ERROR, _T(" CD comms received command %i\n"), NeoCDCommsCommandFIFO[0]);
|
||||||
NeoCDAssyStatus = 1;
|
NeoCDAssyStatus = 1;
|
||||||
bNeoCDLoadSector = true;
|
bNeoCDLoadSector = true;
|
||||||
CDEmuResume();
|
CDEmuResume();
|
||||||
//if (isowav_mode) wav_pause(1);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 8:
|
case 8:
|
||||||
|
@ -2866,6 +2788,7 @@ static void NeoCDProcessCommand()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// For Double Dragon (Early release) - see notes a few pages below..
|
||||||
static INT32 CheckDMASourceForBlankVectorTable(INT32 dmadest, INT32 dmasrc)
|
static INT32 CheckDMASourceForBlankVectorTable(INT32 dmadest, INT32 dmasrc)
|
||||||
{
|
{
|
||||||
if (dmadest == 0) {
|
if (dmadest == 0) {
|
||||||
|
@ -3005,20 +2928,22 @@ static void NeoCDDoDMA()
|
||||||
// - DMA controller program[14] -> 0xFCF5 (PC: 0xC0FD8A)
|
// - DMA controller program[14] -> 0xFCF5 (PC: 0xC0FD8A)
|
||||||
|
|
||||||
// Double Dragon clears the vector table before loading in the
|
// Double Dragon clears the vector table before loading in the
|
||||||
// actual vectors, leading me to believe that there is some sort
|
// actual vectors. Let's just ignore the clearing part
|
||||||
// of vector-cache going on here. Let's just ignore the clearing
|
|
||||||
// so the game doesn't freeze while loading.
|
// so the game doesn't freeze while loading.
|
||||||
|
|
||||||
INT32 OkWriteVect = !CheckDMASourceForBlankVectorTable(NeoCDDMAAddress2, NeoCDDMAAddress1);
|
INT32 OkWriteVect = !CheckDMASourceForBlankVectorTable(NeoCDDMAAddress2, NeoCDDMAAddress1);
|
||||||
|
|
||||||
|
if (!OkWriteVect) {
|
||||||
|
bprintf(0, _T("(DMA) Inhibit blank vector table write into 68k ram-vectspace\n"));
|
||||||
|
}
|
||||||
|
|
||||||
SekIdle(NeoCDDMACount * 1);
|
SekIdle(NeoCDDMACount * 1);
|
||||||
|
|
||||||
while (NeoCDDMACount--) {
|
while (NeoCDDMACount--) {
|
||||||
if (OkWriteVect || NeoCDDMAAddress2 >= 0x80) {
|
if (OkWriteVect || NeoCDDMAAddress2 >= 0x80) {
|
||||||
SekWriteWord(NeoCDDMAAddress2, SekReadWord(NeoCDDMAAddress1));
|
SekWriteWord(NeoCDDMAAddress2, SekReadWord(NeoCDDMAAddress1));
|
||||||
} else {
|
|
||||||
bprintf(0, _T("DMA bytes into rom-vectspace failed @ %X: %X\n"), NeoCDDMAAddress2, SekReadWord(NeoCDDMAAddress1));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
NeoCDDMAAddress1 += 2;
|
NeoCDDMAAddress1 += 2;
|
||||||
NeoCDDMAAddress2 += 2;
|
NeoCDDMAAddress2 += 2;
|
||||||
}
|
}
|
||||||
|
@ -3119,10 +3044,6 @@ static void NeoCDDoDMA()
|
||||||
default: {
|
default: {
|
||||||
bprintf(PRINT_ERROR, _T(" Unknown transfer type 0x%04X (PC: 0x%06X)\n"), NeoCDDMAMode, SekGetPC(-1));
|
bprintf(PRINT_ERROR, _T(" Unknown transfer type 0x%04X (PC: 0x%06X)\n"), NeoCDDMAMode, SekGetPC(-1));
|
||||||
bprintf(PRINT_NORMAL, _T(" ??? : 0x%08X 0x%08X 0x%04X 0x%04X 0x%08X\n"), NeoCDDMAAddress1, NeoCDDMAAddress2, NeoCDDMAValue1, NeoCDDMAValue2, NeoCDDMACount);
|
bprintf(PRINT_NORMAL, _T(" ??? : 0x%08X 0x%08X 0x%04X 0x%04X 0x%08X\n"), NeoCDDMAAddress1, NeoCDDMAAddress2, NeoCDDMAValue1, NeoCDDMAValue2, NeoCDDMACount);
|
||||||
|
|
||||||
extern INT32 bRunPause;
|
|
||||||
bRunPause = 1;
|
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -3163,13 +3084,6 @@ static void NeoCDCommsControl(UINT8 clock, UINT8 send)
|
||||||
|
|
||||||
NeoCDCommsStatusFIFO[0] = NeoCDAssyStatus;
|
NeoCDCommsStatusFIFO[0] = NeoCDAssyStatus;
|
||||||
|
|
||||||
#if 0
|
|
||||||
extern INT32 counter;
|
|
||||||
if (counter) {
|
|
||||||
NeoCDCommsStatusFIFO[0] = counter & 0x0F;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// compute checksum
|
// compute checksum
|
||||||
|
|
||||||
sum = 0;
|
sum = 0;
|
||||||
|
@ -3208,19 +3122,12 @@ static void NeoCDCommsControl(UINT8 clock, UINT8 send)
|
||||||
bNeoCDCommsClock = clock;
|
bNeoCDCommsClock = clock;
|
||||||
}
|
}
|
||||||
|
|
||||||
void NeoCDReadSector()
|
static void NeoCDReadSector()
|
||||||
{
|
{
|
||||||
if ((nff0002 & 0x0500)) {
|
if ((nff0002 & 0x0500)) {
|
||||||
if (NeoCDAssyStatus == 1 && bNeoCDLoadSector) {
|
if (NeoCDAssyStatus == 1 && bNeoCDLoadSector) {
|
||||||
|
|
||||||
// if (LC8951RegistersW[10] & 0x80) {
|
|
||||||
NeoCDSectorLBA++;
|
NeoCDSectorLBA++;
|
||||||
if (isowav_mode) {
|
|
||||||
NeoCDSectorLBA = CDEmuLoadSector(NeoCDSectorLBA, NeoCDSectorData + 4) - 1;
|
|
||||||
} else {
|
|
||||||
NeoCDSectorLBA = CDEmuLoadSector(NeoCDSectorLBA, NeoCDSectorData) - 1;
|
NeoCDSectorLBA = CDEmuLoadSector(NeoCDSectorLBA, NeoCDSectorData) - 1;
|
||||||
}
|
|
||||||
// }
|
|
||||||
|
|
||||||
if (LC8951RegistersW[10] & 0x80) {
|
if (LC8951RegistersW[10] & 0x80) {
|
||||||
LC8951UpdateHeader();
|
LC8951UpdateHeader();
|
||||||
|
@ -3232,13 +3139,11 @@ void NeoCDReadSector()
|
||||||
|
|
||||||
//bprintf(PRINT_IMPORTANT, _T(" Sector %08i (%02i:%02i:%02i) read\n"), NeoCDSectorLBA, NeoCDSectorMin, NeoCDSectorSec, NeoCDSectorFrm);
|
//bprintf(PRINT_IMPORTANT, _T(" Sector %08i (%02i:%02i:%02i) read\n"), NeoCDSectorLBA, NeoCDSectorMin, NeoCDSectorSec, NeoCDSectorFrm);
|
||||||
|
|
||||||
INT32 sectoffs = (isowav_mode) ? 0 : 12;
|
if (NeoCDSectorData[(12 + 4) + 64] == 'g' && !strncmp(NeoCDSectorData + 12 + 4, "Copyright by SNK", 16)) {
|
||||||
|
|
||||||
if (NeoCDSectorData[sectoffs + 4 + 64] == 'g' && !strncmp(NeoCDSectorData + sectoffs + 4, "Copyright by SNK", 16)) {
|
|
||||||
//bprintf(0, _T("\n simulated CDZ protection error\n"));
|
//bprintf(0, _T("\n simulated CDZ protection error\n"));
|
||||||
//bprintf(PRINT_ERROR, _T(" %.70hs\n"), NeoCDSectorData + sectoffs + 4);
|
//bprintf(PRINT_ERROR, _T(" %.70hs\n"), NeoCDSectorData + sectoffs + 4);
|
||||||
|
|
||||||
NeoCDSectorData[sectoffs + 4 + 64] = 'f';
|
NeoCDSectorData[(12 + 4) + 64] = 'f';
|
||||||
|
|
||||||
// LC8951RegistersR[12] = 0x00; // STAT0
|
// LC8951RegistersR[12] = 0x00; // STAT0
|
||||||
}
|
}
|
||||||
|
@ -3253,11 +3158,10 @@ void NeoCDReadSector()
|
||||||
}
|
}
|
||||||
|
|
||||||
bNeoCDLoadSector = true;
|
bNeoCDLoadSector = true;
|
||||||
// bNeoCDLoadSector = false;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
UINT8 __fastcall neogeoReadByteCDROM(UINT32 sekAddress)
|
static UINT8 __fastcall neogeoReadByteCDROM(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
// bprintf(PRINT_NORMAL, _T(" - CDROM: 0x%06X read (byte, PC: 0x%06X)\n"), sekAddress, SekGetPC(-1));
|
// bprintf(PRINT_NORMAL, _T(" - CDROM: 0x%06X read (byte, PC: 0x%06X)\n"), sekAddress, SekGetPC(-1));
|
||||||
|
|
||||||
|
@ -3302,28 +3206,31 @@ UINT8 __fastcall neogeoReadByteCDROM(UINT32 sekAddress)
|
||||||
return ~0;
|
return ~0;
|
||||||
}
|
}
|
||||||
|
|
||||||
UINT16 __fastcall neogeoReadWordCDROM(UINT32 sekAddress)
|
static UINT16 __fastcall neogeoReadWordCDROM(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
// bprintf(PRINT_NORMAL, _T(" - CDROM: 0x%06X read (word, PC: 0x%06X)\n"), sekAddress, SekGetPC(-1));
|
// bprintf(PRINT_NORMAL, _T(" - CDROM: 0x%06X read (word, PC: 0x%06X)\n"), sekAddress, SekGetPC(-1));
|
||||||
|
|
||||||
#if 1
|
|
||||||
switch (sekAddress & 0xFFFF) {
|
switch (sekAddress & 0xFFFF) {
|
||||||
|
case 0x0004:
|
||||||
|
//bprintf(PRINT_IMPORTANT, _T(" - NGCD VBL (read) Interrupt mask -> 0x%04X (PC: 0x%06X)\n"), nff0004, SekGetPC(-1));
|
||||||
|
|
||||||
|
return nff0004;
|
||||||
|
break;
|
||||||
|
|
||||||
case 0x011C:
|
case 0x011C:
|
||||||
return ~((0x10 | (NeoSystem & 3)) << 8);
|
return ~((0x10 | (NeoSystem & 3)) << 8);
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
// bprintf(PRINT_NORMAL, _T(" - NGCD port 0x%06X read (word, PC: 0x%06X)\n"), sekAddress, SekGetPC(-1));
|
// bprintf(PRINT_NORMAL, _T(" - NGCD port 0x%06X read (word, PC: 0x%06X)\n"), sekAddress, SekGetPC(-1));
|
||||||
|
|
||||||
return ~0;
|
return ~0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void __fastcall neogeoWriteByteCDROM(UINT32 sekAddress, UINT8 byteValue)
|
static void __fastcall neogeoWriteByteCDROM(UINT32 sekAddress, UINT8 byteValue)
|
||||||
{
|
{
|
||||||
// bprintf(PRINT_NORMAL, _T(" - Neo Geo CD: 0x%06X -> 0x%02X (PC: 0x%06X)\n"), sekAddress, byteValue, SekGetPC(-1));
|
// bprintf(PRINT_NORMAL, _T(" - Neo Geo CD: 0x%06X -> 0x%02X (PC: 0x%06X)\n"), sekAddress, byteValue, SekGetPC(-1));
|
||||||
|
|
||||||
switch (sekAddress & 0xFFFF) {
|
switch (sekAddress & 0xFFFF) {
|
||||||
//case 0x000E:
|
|
||||||
case 0x000F:
|
case 0x000F:
|
||||||
NeoCDIRQUpdate(byteValue);
|
NeoCDIRQUpdate(byteValue);
|
||||||
break;
|
break;
|
||||||
|
@ -3335,6 +3242,13 @@ void __fastcall neogeoWriteByteCDROM(UINT32 sekAddress, UINT8 byteValue)
|
||||||
case 0x0061:
|
case 0x0061:
|
||||||
if (byteValue & 0x40) {
|
if (byteValue & 0x40) {
|
||||||
NeoCDDoDMA();
|
NeoCDDoDMA();
|
||||||
|
} else
|
||||||
|
if (byteValue == 0) {
|
||||||
|
NeoCDDMAAddress1 = 0;
|
||||||
|
NeoCDDMAAddress2 = 0;
|
||||||
|
NeoCDDMAValue1 = 0;
|
||||||
|
NeoCDDMAValue2 = 0;
|
||||||
|
NeoCDDMACount = 0;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -3379,6 +3293,10 @@ void __fastcall neogeoWriteByteCDROM(UINT32 sekAddress, UINT8 byteValue)
|
||||||
nActiveTransferArea = byteValue;
|
nActiveTransferArea = byteValue;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case 0x0119:
|
||||||
|
bNeoEnableGraphics = (byteValue != 0);
|
||||||
|
break;
|
||||||
|
|
||||||
case 0x0121:
|
case 0x0121:
|
||||||
// bprintf(PRINT_NORMAL, _T(" - NGCD OBJ BUSREQ -> 1 (PC: 0x%06X)\n"), SekGetPC(-1));
|
// bprintf(PRINT_NORMAL, _T(" - NGCD OBJ BUSREQ -> 1 (PC: 0x%06X)\n"), SekGetPC(-1));
|
||||||
NeoSetSpriteSlot(1);
|
NeoSetSpriteSlot(1);
|
||||||
|
@ -3434,9 +3352,6 @@ void __fastcall neogeoWriteByteCDROM(UINT32 sekAddress, UINT8 byteValue)
|
||||||
// bprintf(PRINT_ERROR, _T(" - NGCD port 0x%06X -> 0x%02X (PC: 0x%06X)\n"), sekAddress, byteValue, SekGetPC(-1));
|
// bprintf(PRINT_ERROR, _T(" - NGCD port 0x%06X -> 0x%02X (PC: 0x%06X)\n"), sekAddress, byteValue, SekGetPC(-1));
|
||||||
|
|
||||||
MapVectorTable(!(byteValue == 0xFF));
|
MapVectorTable(!(byteValue == 0xFF));
|
||||||
|
|
||||||
//extern INT32 bRunPause;
|
|
||||||
//bRunPause = 1;
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x016F:
|
case 0x016F:
|
||||||
|
@ -3450,13 +3365,14 @@ void __fastcall neogeoWriteByteCDROM(UINT32 sekAddress, UINT8 byteValue)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x0183: {
|
case 0x0183: {
|
||||||
static UINT8 clara = 0;
|
if (byteValue == 0) {
|
||||||
if (!byteValue && clara) {
|
//bprintf(PRINT_IMPORTANT, _T(" - NGCD Z80 in-reset (PC: 0x%06X, 68k Cyc: %d, Z80 Cyc: %d, Frame: %d)\n"), SekGetPC(-1), SekTotalCycles(), ZetTotalCycles(), nCurrentFrame);
|
||||||
bprintf(PRINT_IMPORTANT, _T(" - NGCD Z80 reset (PC: 0x%06X)\n"), SekGetPC(-1));
|
|
||||||
BurnYM2610Reset();
|
BurnYM2610Reset();
|
||||||
ZetReset();
|
ZetSetRESETLine(1);
|
||||||
|
} else {
|
||||||
|
//bprintf(PRINT_IMPORTANT, _T(" - NGCD Z80 out-reset (PC: 0x%06X, 68k Cyc: %d, Z80 Cyc: %d, Frame: %d)\n"), SekGetPC(-1), SekTotalCycles(), ZetTotalCycles(), nCurrentFrame);
|
||||||
|
ZetSetRESETLine(0);
|
||||||
}
|
}
|
||||||
clara = byteValue;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case 0x01A1:
|
case 0x01A1:
|
||||||
|
@ -3472,7 +3388,7 @@ void __fastcall neogeoWriteByteCDROM(UINT32 sekAddress, UINT8 byteValue)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void __fastcall neogeoWriteWordCDROM(UINT32 sekAddress, UINT16 wordValue)
|
static void __fastcall neogeoWriteWordCDROM(UINT32 sekAddress, UINT16 wordValue)
|
||||||
{
|
{
|
||||||
// bprintf(PRINT_NORMAL, _T(" - NGCD port 0x%06X -> 0x%04X (PC: 0x%06X)\n"), sekAddress, wordValue, SekGetPC(-1));
|
// bprintf(PRINT_NORMAL, _T(" - NGCD port 0x%06X -> 0x%04X (PC: 0x%06X)\n"), sekAddress, wordValue, SekGetPC(-1));
|
||||||
|
|
||||||
|
@ -3485,12 +3401,12 @@ void __fastcall neogeoWriteWordCDROM(UINT32 sekAddress, UINT16 wordValue)
|
||||||
nff0002 = wordValue;
|
nff0002 = wordValue;
|
||||||
|
|
||||||
// LC8951RegistersR[1] |= 0x20;
|
// LC8951RegistersR[1] |= 0x20;
|
||||||
|
break;
|
||||||
|
|
||||||
/* if (nff0002 & 0x0500)
|
case 0x0004:
|
||||||
nNeoCDCyclesIRQPeriod = (INT32)(12000000.0 * nBurnCPUSpeedAdjust / (256.0 * 75.0));
|
//bprintf(PRINT_IMPORTANT, _T(" - NGCD (write) VBL Interrupt mask -> 0x%04X (PC: 0x%06X)\n"), wordValue, SekGetPC(-1));
|
||||||
else
|
|
||||||
nNeoCDCyclesIRQPeriod = (INT32)(12000000.0 * nBurnCPUSpeedAdjust / (256.0 * 75.0));
|
nff0004 = wordValue;
|
||||||
*/
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x000E:
|
case 0x000E:
|
||||||
|
@ -3498,12 +3414,6 @@ void __fastcall neogeoWriteWordCDROM(UINT32 sekAddress, UINT16 wordValue)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
// DMA controller
|
// DMA controller
|
||||||
case 0x0060:
|
|
||||||
if (wordValue & 0x40) {
|
|
||||||
NeoCDDoDMA();
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x0064:
|
case 0x0064:
|
||||||
NeoCDDMAAddress1 &= 0x0000FFFF;
|
NeoCDDMAAddress1 &= 0x0000FFFF;
|
||||||
NeoCDDMAAddress1 |= wordValue << 16;
|
NeoCDDMAAddress1 |= wordValue << 16;
|
||||||
|
@ -3562,7 +3472,7 @@ void __fastcall neogeoWriteWordCDROM(UINT32 sekAddress, UINT16 wordValue)
|
||||||
|
|
||||||
// Reads from / writes to the transfer area
|
// Reads from / writes to the transfer area
|
||||||
|
|
||||||
UINT8 __fastcall neogeoReadByteTransfer(UINT32 sekAddress)
|
static UINT8 __fastcall neogeoReadByteTransfer(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
// if ((sekAddress & 0x0FFFFF) < 16)
|
// if ((sekAddress & 0x0FFFFF) < 16)
|
||||||
// printf(PRINT_NORMAL, _T(" - NGCD port 0x%06X read (byte, PC: 0x%06X)\n"), sekAddress, SekGetPC(-1));
|
// printf(PRINT_NORMAL, _T(" - NGCD port 0x%06X read (byte, PC: 0x%06X)\n"), sekAddress, SekGetPC(-1));
|
||||||
|
@ -3588,7 +3498,7 @@ UINT8 __fastcall neogeoReadByteTransfer(UINT32 sekAddress)
|
||||||
return ~0;
|
return ~0;
|
||||||
}
|
}
|
||||||
|
|
||||||
UINT16 __fastcall neogeoReadWordTransfer(UINT32 sekAddress)
|
static UINT16 __fastcall neogeoReadWordTransfer(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
// if ((sekAddress & 0x0FFFFF) < 16)
|
// if ((sekAddress & 0x0FFFFF) < 16)
|
||||||
// bprintf(PRINT_NORMAL, _T(" - Transfer: 0x%06X read (word, PC: 0x%06X)\n"), sekAddress, SekGetPC(-1));
|
// bprintf(PRINT_NORMAL, _T(" - Transfer: 0x%06X read (word, PC: 0x%06X)\n"), sekAddress, SekGetPC(-1));
|
||||||
|
@ -3612,7 +3522,7 @@ UINT16 __fastcall neogeoReadWordTransfer(UINT32 sekAddress)
|
||||||
return ~0;
|
return ~0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void __fastcall neogeoWriteByteTransfer(UINT32 sekAddress, UINT8 byteValue)
|
static void __fastcall neogeoWriteByteTransfer(UINT32 sekAddress, UINT8 byteValue)
|
||||||
{
|
{
|
||||||
// if ((sekAddress & 0x0FFFFF) < 16)
|
// if ((sekAddress & 0x0FFFFF) < 16)
|
||||||
// bprintf(PRINT_NORMAL, _T(" - Transfer: 0x%06X -> 0x%02X (PC: 0x%06X)\n"), sekAddress, byteValue, SekGetPC(-1));
|
// bprintf(PRINT_NORMAL, _T(" - Transfer: 0x%06X -> 0x%02X (PC: 0x%06X)\n"), sekAddress, byteValue, SekGetPC(-1));
|
||||||
|
@ -3642,7 +3552,7 @@ void __fastcall neogeoWriteByteTransfer(UINT32 sekAddress, UINT8 byteValue)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void __fastcall neogeoWriteWordTransfer(UINT32 sekAddress, UINT16 wordValue)
|
static void __fastcall neogeoWriteWordTransfer(UINT32 sekAddress, UINT16 wordValue)
|
||||||
{
|
{
|
||||||
// if ((sekAddress & 0x0FFFFF) < 16)
|
// if ((sekAddress & 0x0FFFFF) < 16)
|
||||||
// bprintf(PRINT_NORMAL, _T(" - Transfer: 0x%06X -> 0x%04X (PC: 0x%06X)\n"), sekAddress, wordValue, SekGetPC(-1));
|
// bprintf(PRINT_NORMAL, _T(" - Transfer: 0x%06X -> 0x%04X (PC: 0x%06X)\n"), sekAddress, wordValue, SekGetPC(-1));
|
||||||
|
@ -3660,14 +3570,8 @@ void __fastcall neogeoWriteWordTransfer(UINT32 sekAddress, UINT16 wordValue)
|
||||||
YM2610ADPCMAROM[nNeoActiveSlot][nADPCMTransferBank + ((sekAddress & 0x0FFFFF) >> 1)] = wordValue;
|
YM2610ADPCMAROM[nNeoActiveSlot][nADPCMTransferBank + ((sekAddress & 0x0FFFFF) >> 1)] = wordValue;
|
||||||
break;
|
break;
|
||||||
case 4: // Z80
|
case 4: // Z80
|
||||||
if (ZetGetBUSREQLine() == 0) {
|
if ((sekAddress & 0xfffff) >= 0x20000) break;
|
||||||
YM2610ADPCMAROM[nNeoActiveSlot][nADPCMTransferBank + ((sekAddress & 0x0FFFFF) >> 1)] = wordValue;
|
|
||||||
} else {
|
|
||||||
// What's the deal with the high bits? Some games (Karnov's Revenge) will spew onto
|
|
||||||
// the sound cpu which causes issues - so we ignore all writes with the high bits set.
|
|
||||||
if ((sekAddress & 0xfffff) >= 0x20000 || (wordValue & 0xFF00)) break;
|
|
||||||
NeoZ80ROMActive[(sekAddress & 0x1FFFF) >> 1] = wordValue;
|
NeoZ80ROMActive[(sekAddress & 0x1FFFF) >> 1] = wordValue;
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
case 5: // Text
|
case 5: // Text
|
||||||
NeoTextRAM[(sekAddress & 0x3FFFF) >> 1] = wordValue;
|
NeoTextRAM[(sekAddress & 0x3FFFF) >> 1] = wordValue;
|
||||||
|
@ -3676,7 +3580,7 @@ void __fastcall neogeoWriteWordTransfer(UINT32 sekAddress, UINT16 wordValue)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
UINT16 __fastcall neogeoCDReadWord68KProgram(UINT32 sekAddress)
|
static UINT16 __fastcall neogeoCDReadWord68KProgram(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
if (sekAddress < 0x80 && NeoCDVectorSwitch == 0) {
|
if (sekAddress < 0x80 && NeoCDVectorSwitch == 0) {
|
||||||
return *((UINT16*)(NeoVectorActive + sekAddress));
|
return *((UINT16*)(NeoVectorActive + sekAddress));
|
||||||
|
@ -3685,7 +3589,7 @@ UINT16 __fastcall neogeoCDReadWord68KProgram(UINT32 sekAddress)
|
||||||
return *((UINT16*)(Neo68KROMActive + sekAddress));
|
return *((UINT16*)(Neo68KROMActive + sekAddress));
|
||||||
}
|
}
|
||||||
|
|
||||||
UINT8 __fastcall neogeoCDReadByte68KProgram(UINT32 sekAddress)
|
static UINT8 __fastcall neogeoCDReadByte68KProgram(UINT32 sekAddress)
|
||||||
{
|
{
|
||||||
if (sekAddress < 0x80 && NeoCDVectorSwitch == 0) {
|
if (sekAddress < 0x80 && NeoCDVectorSwitch == 0) {
|
||||||
return NeoVectorActive[sekAddress ^ 1];
|
return NeoVectorActive[sekAddress ^ 1];
|
||||||
|
@ -3762,9 +3666,6 @@ static INT32 neogeoReset()
|
||||||
#if 1 && defined FBA_DEBUG
|
#if 1 && defined FBA_DEBUG
|
||||||
if (nNeoSystemType & NEO_SYS_CD) {
|
if (nNeoSystemType & NEO_SYS_CD) {
|
||||||
bprintf(PRINT_IMPORTANT, _T(" - Emulating Neo CD system.\n"));
|
bprintf(PRINT_IMPORTANT, _T(" - Emulating Neo CD system.\n"));
|
||||||
|
|
||||||
// exit WAV object if needed
|
|
||||||
//if (isowav_mode) wav_exit();
|
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
@ -3853,9 +3754,12 @@ static INT32 neogeoReset()
|
||||||
memset(NeoCDOBJBankUpdate, 0, sizeof(NeoCDOBJBankUpdate));
|
memset(NeoCDOBJBankUpdate, 0, sizeof(NeoCDOBJBankUpdate));
|
||||||
|
|
||||||
LC8951Reset();
|
LC8951Reset();
|
||||||
|
|
||||||
|
CDEmuStop();
|
||||||
}
|
}
|
||||||
|
|
||||||
ZetSetBUSREQLine(0);
|
ZetSetBUSREQLine(0);
|
||||||
|
ZetSetRESETLine(0);
|
||||||
|
|
||||||
SekReset();
|
SekReset();
|
||||||
ZetReset();
|
ZetReset();
|
||||||
|
@ -3882,6 +3786,7 @@ static INT32 neogeoReset()
|
||||||
nNeoCDIRQVector = 0;
|
nNeoCDIRQVector = 0;
|
||||||
nNeoCDIRQVectorAck = 0;
|
nNeoCDIRQVectorAck = 0;
|
||||||
nff0002 = 0;
|
nff0002 = 0;
|
||||||
|
nff0004 = 0;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -4459,6 +4364,8 @@ INT32 NeoExit()
|
||||||
fatfury2mode = 0;
|
fatfury2mode = 0;
|
||||||
vlinermode = 0;
|
vlinermode = 0;
|
||||||
|
|
||||||
|
nNeoSystemType = 0;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4531,9 +4438,6 @@ static void NeoStandardInputs(INT32 nBank)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#if 0
|
|
||||||
#define NeoSekRun SekRun
|
|
||||||
#else
|
|
||||||
static INT32 NeoSekRun(const INT32 nCycles)
|
static INT32 NeoSekRun(const INT32 nCycles)
|
||||||
{
|
{
|
||||||
INT32 nCyclesExecutedTotal = 0, nOldCyclesSegment = nCyclesSegment;
|
INT32 nCyclesExecutedTotal = 0, nOldCyclesSegment = nCyclesSegment;
|
||||||
|
@ -4568,7 +4472,6 @@ static INT32 NeoSekRun(const INT32 nCycles)
|
||||||
|
|
||||||
return nCyclesExecutedTotal;
|
return nCyclesExecutedTotal;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
INT32 NeoFrame()
|
INT32 NeoFrame()
|
||||||
{
|
{
|
||||||
|
@ -4576,7 +4479,9 @@ INT32 NeoFrame()
|
||||||
if (nNeoSystemType & NEO_SYS_CART) {
|
if (nNeoSystemType & NEO_SYS_CART) {
|
||||||
memset(Neo68KRAM, 0, 0x010000);
|
memset(Neo68KRAM, 0, 0x010000);
|
||||||
}
|
}
|
||||||
|
if (nNeoSystemType & NEO_SYS_CD) {
|
||||||
|
memset(Neo68KROM[0], 0, nCodeSize[0]);
|
||||||
|
}
|
||||||
neogeoReset();
|
neogeoReset();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4783,20 +4688,6 @@ INT32 NeoFrame()
|
||||||
nuPD4990ATicks = nCyclesExtra[0];
|
nuPD4990ATicks = nCyclesExtra[0];
|
||||||
|
|
||||||
// Run 68000
|
// Run 68000
|
||||||
|
|
||||||
|
|
||||||
if (isowav_mode) {
|
|
||||||
if ((nNeoSystemType & NEO_SYS_CD) && (nff0002 & 0x0050)) {
|
|
||||||
nIRQAcknowledge &= ~0x10;
|
|
||||||
NeoCDIRQUpdate(0);
|
|
||||||
|
|
||||||
if (nff0002 & 0x0500) {
|
|
||||||
NeoCDReadSector();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
nCyclesSegment = nSekCyclesScanline * 24;
|
nCyclesSegment = nSekCyclesScanline * 24;
|
||||||
while (SekTotalCycles() < nCyclesSegment) {
|
while (SekTotalCycles() < nCyclesSegment) {
|
||||||
|
|
||||||
|
@ -4967,8 +4858,10 @@ INT32 NeoFrame()
|
||||||
NeoRenderText(); // Render text layer
|
NeoRenderText(); // Render text layer
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ( ((nNeoSystemType & NEO_SYS_CD) && (nff0004 & 0x0030) == 0x0030) || (~nNeoSystemType & NEO_SYS_CD) ) {
|
||||||
nIRQAcknowledge &= ~4;
|
nIRQAcknowledge &= ~4;
|
||||||
SekSetIRQLine(nVBLankIRQ, CPU_IRQSTATUS_ACK);
|
SekSetIRQLine(nVBLankIRQ, CPU_IRQSTATUS_ACK);
|
||||||
|
}
|
||||||
|
|
||||||
#if 0 || defined LOG_IRQ
|
#if 0 || defined LOG_IRQ
|
||||||
bprintf(PRINT_NORMAL, _T(" - VBLank.\n"));
|
bprintf(PRINT_NORMAL, _T(" - VBLank.\n"));
|
||||||
|
@ -5062,7 +4955,7 @@ INT32 NeoFrame()
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pBurnSoundOut) {
|
if (pBurnSoundOut) {
|
||||||
if (!(LC8951RegistersW[10] & 4))
|
if ((nNeoSystemType & NEO_SYS_CD) && !(LC8951RegistersW[10] & 4))
|
||||||
CDEmuGetSoundBuffer(pBurnSoundOut, nBurnSoundLen);
|
CDEmuGetSoundBuffer(pBurnSoundOut, nBurnSoundLen);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -68,6 +68,8 @@ static UINT8 DrvDips[1];
|
||||||
static UINT8 DrvReset;
|
static UINT8 DrvReset;
|
||||||
static UINT8 DrvInputs[6];
|
static UINT8 DrvInputs[6];
|
||||||
|
|
||||||
|
static INT32 is_shufshot = 0;
|
||||||
|
|
||||||
static INT16 DrvAnalogPort0 = 0;
|
static INT16 DrvAnalogPort0 = 0;
|
||||||
static INT16 DrvAnalogPort1 = 0;
|
static INT16 DrvAnalogPort1 = 0;
|
||||||
static INT16 DrvAnalogPort2 = 0;
|
static INT16 DrvAnalogPort2 = 0;
|
||||||
|
@ -2206,6 +2208,7 @@ static void __fastcall common32_main_write_word(UINT32 address, UINT16 data)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ((address&0xffff00) != 0x61ff00)
|
||||||
bprintf (0, _T("MWW: %5.5x, %4.4x\n"), address, data);
|
bprintf (0, _T("MWW: %5.5x, %4.4x\n"), address, data);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2274,6 +2277,7 @@ static void __fastcall common32_main_write_byte(UINT32 address, UINT8 data)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ((address&0xffff00) != 0x61ff00)
|
||||||
bprintf (0, _T("MWB: %5.5x, %2.2x\n"), address, data);
|
bprintf (0, _T("MWB: %5.5x, %2.2x\n"), address, data);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2287,6 +2291,17 @@ static UINT16 track_read_8bit(INT32 player)
|
||||||
return (BurnTrackballRead(player, 0) & 0xff) | ((BurnTrackballRead(player, 1) & 0xff) << 8);
|
return (BurnTrackballRead(player, 0) & 0xff) | ((BurnTrackballRead(player, 1) & 0xff) << 8);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static INT32 shufshot_weird_y(INT16 ana)
|
||||||
|
{
|
||||||
|
// todo: revisit at a later time.
|
||||||
|
// "git 'r dun"-style
|
||||||
|
if (ana > 1024) ana = 1024;
|
||||||
|
if (ana < -1024) ana = -1024;
|
||||||
|
ana /= 256; // -4 - +4
|
||||||
|
ana *= 0.9; // tone it down a bit..
|
||||||
|
return (ana);
|
||||||
|
}
|
||||||
|
|
||||||
static UINT32 track_read_4bit(INT32 player)
|
static UINT32 track_read_4bit(INT32 player)
|
||||||
{
|
{
|
||||||
if (tb_last_read[player] != scanline) {
|
if (tb_last_read[player] != scanline) {
|
||||||
|
@ -2306,6 +2321,12 @@ static UINT32 track_read_4bit(INT32 player)
|
||||||
else if (dy > 0x80) dy -= 0x100;
|
else if (dy > 0x80) dy -= 0x100;
|
||||||
if (dy > 7) dy = 7;
|
if (dy > 7) dy = 7;
|
||||||
else if (dy < -7) dy = -7;
|
else if (dy < -7) dy = -7;
|
||||||
|
|
||||||
|
if (is_shufshot) {
|
||||||
|
// keep shufshot happy...
|
||||||
|
dy = shufshot_weird_y((player == 0) ? DrvAnalogPort1 : DrvAnalogPort3);
|
||||||
|
}
|
||||||
|
|
||||||
tb_effy[player] = (tb_effy[player] + dy) & 0xff;
|
tb_effy[player] = (tb_effy[player] + dy) & 0xff;
|
||||||
INT32 upper = tb_effy[player] & 15;
|
INT32 upper = tb_effy[player] & 15;
|
||||||
|
|
||||||
|
@ -2812,8 +2833,9 @@ static INT32 DrvGetRoms(bool bLoad)
|
||||||
if (bLoad) {
|
if (bLoad) {
|
||||||
if (BurnLoadRom(pSndLoad[bank] + 1, i, 2)) return 1;
|
if (BurnLoadRom(pSndLoad[bank] + 1, i, 2)) return 1;
|
||||||
}
|
}
|
||||||
if (nSndROMLen[1]) {
|
if (nSndROMLen[1] || is_shufshot) {
|
||||||
// wcbowl,wcbowldx,wcbowl{140,165,161,16} have bank1 and 0x200000 spacing
|
// wcbowl,wcbowldx,wcbowl{140,165,161,16} have bank1 and 0x200000 spacing
|
||||||
|
// shufshot has 0x200000 spacing but only bank0
|
||||||
pSndLoad[bank] += 0x200000;
|
pSndLoad[bank] += 0x200000;
|
||||||
} else {
|
} else {
|
||||||
pSndLoad[bank] += ri.nLen * 2;
|
pSndLoad[bank] += ri.nLen * 2;
|
||||||
|
@ -3000,6 +3022,8 @@ static INT32 DrvExit()
|
||||||
|
|
||||||
Trackball_Type = -1;
|
Trackball_Type = -1;
|
||||||
|
|
||||||
|
is_shufshot = 0;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4821,6 +4845,7 @@ STD_ROM_FN(shufshot)
|
||||||
static INT32 ShufshotInit()
|
static INT32 ShufshotInit()
|
||||||
{
|
{
|
||||||
Trackball_Type = TB_TYPE0;
|
Trackball_Type = TB_TYPE0;
|
||||||
|
is_shufshot = 1;
|
||||||
|
|
||||||
return Common32BitInit(0x111a, 1, 0);
|
return Common32BitInit(0x111a, 1, 0);
|
||||||
}
|
}
|
||||||
|
|
|
@ -150,6 +150,10 @@ TCHAR* LabelCheck(TCHAR* s, TCHAR* pszLabel);
|
||||||
TCHAR* ExtractFilename(TCHAR* fullname);
|
TCHAR* ExtractFilename(TCHAR* fullname);
|
||||||
TCHAR* DriverToName(UINT32 nDrv);
|
TCHAR* DriverToName(UINT32 nDrv);
|
||||||
UINT32 NameToDriver(TCHAR* szName);
|
UINT32 NameToDriver(TCHAR* szName);
|
||||||
|
TCHAR *StrReplace(TCHAR *str, TCHAR find, TCHAR replace);
|
||||||
|
TCHAR *StrLower(TCHAR *str);
|
||||||
|
TCHAR *FileExt(TCHAR *str);
|
||||||
|
bool IsFileExt(TCHAR *str, TCHAR *ext);
|
||||||
|
|
||||||
extern INT32 bDoGamma;
|
extern INT32 bDoGamma;
|
||||||
extern INT32 bHardwareGammaOnly;
|
extern INT32 bHardwareGammaOnly;
|
||||||
|
|
|
@ -477,3 +477,45 @@ UINT32 NameToDriver(TCHAR* szName)
|
||||||
|
|
||||||
return nDrv;
|
return nDrv;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TCHAR *FileExt(TCHAR *str)
|
||||||
|
{
|
||||||
|
TCHAR *dot = _tcsrchr(str, _T('.'));
|
||||||
|
|
||||||
|
return (dot) ? StrLower(dot) : str;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool IsFileExt(TCHAR *str, TCHAR *ext)
|
||||||
|
{
|
||||||
|
return (_tcsicmp(ext, FileExt(str)) == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
TCHAR *StrReplace(TCHAR *str, TCHAR find, TCHAR replace)
|
||||||
|
{
|
||||||
|
INT32 length = _tcslen(str);
|
||||||
|
|
||||||
|
for (INT32 i = 0; i < length; i++) {
|
||||||
|
if (str[i] == find) str[i] = replace;
|
||||||
|
}
|
||||||
|
|
||||||
|
return str;
|
||||||
|
}
|
||||||
|
|
||||||
|
// StrLower() - leaves str untouched, returns modified string
|
||||||
|
TCHAR *StrLower(TCHAR *str)
|
||||||
|
{
|
||||||
|
static TCHAR szBuffer[256] = _T("");
|
||||||
|
INT32 length = _tcslen(str);
|
||||||
|
|
||||||
|
if (length > 255) length = 255;
|
||||||
|
|
||||||
|
for (INT32 i = 0; i < length; i++) {
|
||||||
|
if (str[i] >= _T('A') && str[i] <= _T('Z'))
|
||||||
|
szBuffer[i] = (str[i] + _T(' '));
|
||||||
|
else
|
||||||
|
szBuffer[i] = str[i];
|
||||||
|
}
|
||||||
|
szBuffer[length] = 0;
|
||||||
|
|
||||||
|
return &szBuffer[0];
|
||||||
|
}
|
||||||
|
|
|
@ -803,7 +803,7 @@ BEGIN
|
||||||
EDITTEXT IDC_NCD_TEXTPUBLISHER,64,245,286,12,ES_AUTOHSCROLL | ES_READONLY | NOT WS_BORDER | NOT WS_TABSTOP
|
EDITTEXT IDC_NCD_TEXTPUBLISHER,64,245,286,12,ES_AUTOHSCROLL | ES_READONLY | NOT WS_BORDER | NOT WS_TABSTOP
|
||||||
EDITTEXT IDC_NCD_TEXTIMAGE,64,259,286,12,ES_AUTOHSCROLL | ES_READONLY | NOT WS_BORDER | NOT WS_TABSTOP
|
EDITTEXT IDC_NCD_TEXTIMAGE,64,259,286,12,ES_AUTOHSCROLL | ES_READONLY | NOT WS_BORDER | NOT WS_TABSTOP
|
||||||
EDITTEXT IDC_NCD_TEXTAUDIO,64,273,50,12,ES_AUTOHSCROLL | ES_READONLY | NOT WS_BORDER | NOT WS_TABSTOP
|
EDITTEXT IDC_NCD_TEXTAUDIO,64,273,50,12,ES_AUTOHSCROLL | ES_READONLY | NOT WS_BORDER | NOT WS_TABSTOP
|
||||||
CONTROL "Scan for ISO only",IDC_NCD_SISO_ONLY_CHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,442,255,71,10
|
// CONTROL "Scan for ISO only",IDC_NCD_SISO_ONLY_CHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,442,255,71,10
|
||||||
END
|
END
|
||||||
|
|
||||||
|
|
||||||
|
@ -977,7 +977,7 @@ BEGIN
|
||||||
MENUITEM "Start Neo Geo Multi-slot...\tCtrl+F6",MENU_START_NEOGEO_MVS
|
MENUITEM "Start Neo Geo Multi-slot...\tCtrl+F6",MENU_START_NEOGEO_MVS
|
||||||
MENUITEM SEPARATOR
|
MENUITEM SEPARATOR
|
||||||
MENUITEM "Load Neo Geo CDZ game...\tCtrl+F8", MENU_LOAD_NEOCD
|
MENUITEM "Load Neo Geo CDZ game...\tCtrl+F8", MENU_LOAD_NEOCD
|
||||||
MENUITEM "Select CD image (ISO/CUE)...\tCtrl+Shift+F12", MENU_CDIMAGE
|
MENUITEM "Select CD image (CUE/CCD)...\tCtrl+Shift+F12", MENU_CDIMAGE
|
||||||
MENUITEM "Start Neo Geo CDZ...\tCtrl+Shift+F6", MENU_START_NEOGEO_CD
|
MENUITEM "Start Neo Geo CDZ...\tCtrl+Shift+F6", MENU_START_NEOGEO_CD
|
||||||
MENUITEM SEPARATOR
|
MENUITEM SEPARATOR
|
||||||
MENUITEM "Exit game\tCtrl+F4", MENU_QUIT, GRAYED
|
MENUITEM "Exit game\tCtrl+F4", MENU_QUIT, GRAYED
|
||||||
|
|
|
@ -224,6 +224,7 @@ extern TCHAR szAppRomPaths[DIRS_MAX][MAX_PATH];
|
||||||
int DrvInit(int nDrvNum, bool bRestore);
|
int DrvInit(int nDrvNum, bool bRestore);
|
||||||
int DrvInitCallback(); // Used when Burn library needs to load a game. DrvInit(nBurnSelect, false)
|
int DrvInitCallback(); // Used when Burn library needs to load a game. DrvInit(nBurnSelect, false)
|
||||||
int DrvExit();
|
int DrvExit();
|
||||||
|
void NeoCDZRateChangeback();
|
||||||
|
|
||||||
// burn_shift
|
// burn_shift
|
||||||
extern INT32 BurnShiftEnabled;
|
extern INT32 BurnShiftEnabled;
|
||||||
|
|
|
@ -10,6 +10,8 @@ TCHAR szAppRomPaths[DIRS_MAX][MAX_PATH] = { { _T("") }, { _T("") }, { _T("") },
|
||||||
|
|
||||||
static bool bSaveRAM = false;
|
static bool bSaveRAM = false;
|
||||||
|
|
||||||
|
static INT32 nNeoCDZnAudSampleRateSave = 0;
|
||||||
|
|
||||||
static int DrvBzipOpen()
|
static int DrvBzipOpen()
|
||||||
{
|
{
|
||||||
BzipOpen(false);
|
BzipOpen(false);
|
||||||
|
@ -118,6 +120,24 @@ int __cdecl DrvCartridgeAccess(BurnCartrigeCommand nCommand)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void NeoCDZRateChangeback()
|
||||||
|
{
|
||||||
|
if (nNeoCDZnAudSampleRateSave != 0) {
|
||||||
|
bprintf(PRINT_IMPORTANT, _T("Switching sound rate back to user-selected %dhz\n"), nNeoCDZnAudSampleRateSave);
|
||||||
|
nAudSampleRate[nAudSelect] = nNeoCDZnAudSampleRateSave;
|
||||||
|
nNeoCDZnAudSampleRateSave = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void NeoCDZRateChange()
|
||||||
|
{
|
||||||
|
if (nAudSampleRate[nAudSelect] != 44100) {
|
||||||
|
nNeoCDZnAudSampleRateSave = nAudSampleRate[nAudSelect];
|
||||||
|
bprintf(PRINT_IMPORTANT, _T("Switching sound rate to 44100hz (from %dhz) as required by NeoGeo CDZ\n"), nNeoCDZnAudSampleRateSave);
|
||||||
|
nAudSampleRate[nAudSelect] = 44100; // force 44100hz for CDDA
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int DrvInit(int nDrvNum, bool bRestore)
|
int DrvInit(int nDrvNum, bool bRestore)
|
||||||
{
|
{
|
||||||
int nStatus;
|
int nStatus;
|
||||||
|
@ -145,6 +165,8 @@ int DrvInit(int nDrvNum, bool bRestore)
|
||||||
POST_INITIALISE_MESSAGE;
|
POST_INITIALISE_MESSAGE;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
NeoCDZRateChange();
|
||||||
}
|
}
|
||||||
|
|
||||||
{ // Init input and audio, save blitter init for later. (reduce # of mode changes, nice for emu front-ends)
|
{ // Init input and audio, save blitter init for later. (reduce # of mode changes, nice for emu front-ends)
|
||||||
|
@ -168,6 +190,7 @@ int DrvInit(int nDrvNum, bool bRestore)
|
||||||
}
|
}
|
||||||
|
|
||||||
nStatus = DoLibInit(); // Init the Burn library's driver
|
nStatus = DoLibInit(); // Init the Burn library's driver
|
||||||
|
|
||||||
if (nStatus) {
|
if (nStatus) {
|
||||||
if (nStatus & 2) {
|
if (nStatus & 2) {
|
||||||
BurnDrvExit(); // Exit the driver
|
BurnDrvExit(); // Exit the driver
|
||||||
|
@ -178,6 +201,8 @@ int DrvInit(int nDrvNum, bool bRestore)
|
||||||
FBAPopupDisplay(PUF_TYPE_WARNING);
|
FBAPopupDisplay(PUF_TYPE_WARNING);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
NeoCDZRateChangeback();
|
||||||
|
|
||||||
POST_INITIALISE_MESSAGE;
|
POST_INITIALISE_MESSAGE;
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
@ -230,6 +255,8 @@ int DrvInitCallback()
|
||||||
int DrvExit()
|
int DrvExit()
|
||||||
{
|
{
|
||||||
if (bDrvOkay) {
|
if (bDrvOkay) {
|
||||||
|
NeoCDZRateChangeback();
|
||||||
|
|
||||||
StopReplay();
|
StopReplay();
|
||||||
|
|
||||||
VidExit();
|
VidExit();
|
||||||
|
|
|
@ -1043,6 +1043,8 @@ int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE, LPSTR lpCmdLine, int nShowCmd
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
NeoCDZRateChangeback(); // Change back temp CDZ rate before saving
|
||||||
|
|
||||||
ConfigAppSave(); // Save config for the application
|
ConfigAppSave(); // Save config for the application
|
||||||
|
|
||||||
AppExit(); // Exit the application
|
AppExit(); // Exit the application
|
||||||
|
|
|
@ -163,13 +163,13 @@ void iso9660_ReadOffset(unsigned char *Dest, FILE* fp, unsigned int lOffset, uns
|
||||||
if(fp == NULL) return;
|
if(fp == NULL) return;
|
||||||
if (Dest == NULL) return;
|
if (Dest == NULL) return;
|
||||||
|
|
||||||
fseek(fp, lOffset, SEEK_SET);
|
fseek(fp, lOffset + 16, SEEK_SET);
|
||||||
fread(Dest, lLength, lSize, fp);
|
fread(Dest, lLength, lSize, fp);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void NeoCDList_iso9660_CheckDirRecord(FILE* fp, int nSector)
|
static void NeoCDList_iso9660_CheckDirRecord(FILE* fp, int nSector)
|
||||||
{
|
{
|
||||||
int nSectorLength = 2048;
|
int nSectorLength = 2352;
|
||||||
//int nFile = 0;
|
//int nFile = 0;
|
||||||
unsigned int lBytesRead = 0;
|
unsigned int lBytesRead = 0;
|
||||||
//int nLen = 0;
|
//int nLen = 0;
|
||||||
|
@ -213,7 +213,7 @@ static void NeoCDList_iso9660_CheckDirRecord(FILE* fp, int nSector)
|
||||||
iso9660_ReadOffset(nLenDR, fp, lOffset + 1, 1, sizeof(unsigned char));
|
iso9660_ReadOffset(nLenDR, fp, lOffset + 1, 1, sizeof(unsigned char));
|
||||||
|
|
||||||
if(nLenDR[0] < 0x22) {
|
if(nLenDR[0] < 0x22) {
|
||||||
lOffset += (2048 - lBytesRead);
|
lOffset += (nSectorLength - lBytesRead);
|
||||||
lBytesRead = 0;
|
lBytesRead = 0;
|
||||||
bNewSector = true;
|
bNewSector = true;
|
||||||
continue;
|
continue;
|
||||||
|
@ -234,7 +234,7 @@ static void NeoCDList_iso9660_CheckDirRecord(FILE* fp, int nSector)
|
||||||
unsigned int nValue = 0;
|
unsigned int nValue = 0;
|
||||||
sscanf(szValue, "%x", &nValue);
|
sscanf(szValue, "%x", &nValue);
|
||||||
|
|
||||||
iso9660_ReadOffset(Data, fp, nValue * 2048, 0x10a, sizeof(unsigned char));
|
iso9660_ReadOffset(Data, fp, nValue * nSectorLength, 0x10a, sizeof(unsigned char));
|
||||||
|
|
||||||
char szData[8];
|
char szData[8];
|
||||||
sprintf(szData, "%c%c%c%c%c%c%c", Data[0x100], Data[0x101], Data[0x102], Data[0x103], Data[0x104], Data[0x105], Data[0x106]);
|
sprintf(szData, "%c%c%c%c%c%c%c", Data[0x100], Data[0x101], Data[0x102], Data[0x103], Data[0x104], Data[0x105], Data[0x106]);
|
||||||
|
@ -346,7 +346,7 @@ static int NeoCDList_CheckISO(TCHAR* pszFile)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Make sure we have a valid ISO file extension...
|
// Make sure we have a valid ISO file extension...
|
||||||
if(_tcsstr(pszFile, _T(".iso")) || _tcsstr(pszFile, _T(".ISO")) )
|
if (IsFileExt(pszFile, _T(".img")) || IsFileExt(pszFile, _T(".bin")))
|
||||||
{
|
{
|
||||||
FILE* fp = _tfopen(pszFile, _T("rb"));
|
FILE* fp = _tfopen(pszFile, _T("rb"));
|
||||||
if(fp)
|
if(fp)
|
||||||
|
@ -359,20 +359,18 @@ static int NeoCDList_CheckISO(TCHAR* pszFile)
|
||||||
fseek(fp, 0, SEEK_END);
|
fseek(fp, 0, SEEK_END);
|
||||||
unsigned int lSize = 0;
|
unsigned int lSize = 0;
|
||||||
lSize = ftell(fp);
|
lSize = ftell(fp);
|
||||||
//rewind(fp);
|
|
||||||
fseek(fp, 0, SEEK_SET);
|
fseek(fp, 0, SEEK_SET);
|
||||||
|
|
||||||
// If it has at least 16 sectors proceed
|
// If it has at least 16 sectors proceed
|
||||||
if(lSize > (2048 * 16))
|
if(lSize > (2352 * 16))
|
||||||
{
|
{
|
||||||
// Check for Standard ISO9660 Identifier
|
// Check for Standard ISO9660 Identifier
|
||||||
unsigned char IsoHeader[2048 * 16 + 1];
|
|
||||||
unsigned char IsoCheck[6];
|
unsigned char IsoCheck[6];
|
||||||
|
|
||||||
fread(IsoHeader, 1, 2048 * 16 + 1, fp); // advance to sector 16 and PVD Field 2
|
// advance to sector 16 and PVD Field 2
|
||||||
fread(IsoCheck, 1, 5, fp); // get Standard Identifier Field from PVD
|
iso9660_ReadOffset(&IsoCheck[0], fp, 2352 * 16 + 1, 1, 5); // get Standard Identifier Field from PVD
|
||||||
|
|
||||||
// Verify that we have indeed a valid ISO9660 MODE1/2048
|
// Verify that we have indeed a valid ISO9660 MODE1/2352
|
||||||
if(!memcmp(IsoCheck, "CD001", 5))
|
if(!memcmp(IsoCheck, "CD001", 5))
|
||||||
{
|
{
|
||||||
//bprintf(PRINT_NORMAL, _T(" Standard ISO9660 Identifier Found. \n"));
|
//bprintf(PRINT_NORMAL, _T(" Standard ISO9660 Identifier Found. \n"));
|
||||||
|
@ -381,7 +379,7 @@ static int NeoCDList_CheckISO(TCHAR* pszFile)
|
||||||
// Get Volume Descriptor Header
|
// Get Volume Descriptor Header
|
||||||
memset(&vdh, 0, sizeof(vdh));
|
memset(&vdh, 0, sizeof(vdh));
|
||||||
//memcpy(&vdh, iso9660_ReadOffset(fp, (2048 * 16), sizeof(vdh)), sizeof(vdh));
|
//memcpy(&vdh, iso9660_ReadOffset(fp, (2048 * 16), sizeof(vdh)), sizeof(vdh));
|
||||||
iso9660_ReadOffset((unsigned char*)&vdh, fp, 2048 * 16, 1, sizeof(vdh));
|
iso9660_ReadOffset((unsigned char*)&vdh, fp, 16 * 2352, 1, sizeof(vdh));
|
||||||
|
|
||||||
// Check for a valid Volume Descriptor Type
|
// Check for a valid Volume Descriptor Type
|
||||||
if(vdh.vdtype == 0x01)
|
if(vdh.vdtype == 0x01)
|
||||||
|
@ -392,7 +390,7 @@ static int NeoCDList_CheckISO(TCHAR* pszFile)
|
||||||
iso9660_PVD pvd;
|
iso9660_PVD pvd;
|
||||||
memset(&pvd, 0, sizeof(pvd));
|
memset(&pvd, 0, sizeof(pvd));
|
||||||
//memcpy(&pvd, iso9660_ReadOffset(fp, (2048 * 16), sizeof(pvd)), sizeof(pvd));
|
//memcpy(&pvd, iso9660_ReadOffset(fp, (2048 * 16), sizeof(pvd)), sizeof(pvd));
|
||||||
iso9660_ReadOffset((unsigned char*)&pvd, fp, 2048 * 16, 1, sizeof(pvd));
|
iso9660_ReadOffset((unsigned char*)&pvd, fp, 2352 * 16, 1, sizeof(pvd));
|
||||||
|
|
||||||
// ROOT DIRECTORY RECORD
|
// ROOT DIRECTORY RECORD
|
||||||
|
|
||||||
|
@ -409,13 +407,12 @@ static int NeoCDList_CheckISO(TCHAR* pszFile)
|
||||||
// Convert HEX string to Decimal
|
// Convert HEX string to Decimal
|
||||||
sscanf(szRootSector, "%X", &nRootSector);
|
sscanf(szRootSector, "%X", &nRootSector);
|
||||||
#else
|
#else
|
||||||
// Just read from the file directly at the correct offset (0x8000 + 0x9e for the start of the root directory record)
|
// Just read from the file directly at the correct offset (SECTOR_SIZE * 16 + 0x9e for the start of the root directory record)
|
||||||
unsigned char buffer[8];
|
unsigned char buffer[8];
|
||||||
char szRootSector[32];
|
char szRootSector[32];
|
||||||
unsigned int nRootSector = 0;
|
unsigned int nRootSector = 0;
|
||||||
|
|
||||||
fseek(fp, 0x809e, SEEK_SET);
|
iso9660_ReadOffset(&buffer[0], fp, 2352 * 16 + 0x9e, 1, 8);
|
||||||
fread(buffer, 1, 8, fp);
|
|
||||||
|
|
||||||
sprintf(szRootSector, "%02x%02x%02x%02x", buffer[4], buffer[5], buffer[6], buffer[7]);
|
sprintf(szRootSector, "%02x%02x%02x%02x", buffer[4], buffer[5], buffer[6], buffer[7]);
|
||||||
|
|
||||||
|
@ -459,10 +456,11 @@ int GetNeoGeoCD_Identifier()
|
||||||
}
|
}
|
||||||
|
|
||||||
// Make sure we have a valid ISO file extension...
|
// Make sure we have a valid ISO file extension...
|
||||||
if(_tcsstr(GetIsoPath(), _T(".iso")) || _tcsstr(GetIsoPath(), _T(".ISO")) )
|
if (IsFileExt(GetIsoPath(), _T(".img")) || IsFileExt(GetIsoPath(), _T(".bin")))
|
||||||
{
|
{
|
||||||
if(_tfopen(GetIsoPath(), _T("rb")))
|
if(_tfopen(GetIsoPath(), _T("rb")))
|
||||||
{
|
{
|
||||||
|
bprintf(0, _T("NeoCDList: checking %s\n"), GetIsoPath());
|
||||||
// Read ISO and look for 68K ROM standard program header, ID is always there
|
// Read ISO and look for 68K ROM standard program header, ID is always there
|
||||||
// Note: This function works very quick, doesn't compromise performance :)
|
// Note: This function works very quick, doesn't compromise performance :)
|
||||||
// it just read each sector first 264 bytes aproximately only.
|
// it just read each sector first 264 bytes aproximately only.
|
||||||
|
@ -476,7 +474,7 @@ int GetNeoGeoCD_Identifier()
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
|
|
||||||
bprintf(PRINT_NORMAL, _T(" File doesn't have a valid ISO extension [ .iso / .ISO ] \n"));
|
bprintf(PRINT_NORMAL, _T(" File doesn't have a valid ISO extension [ .img / .bin ] \n"));
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -51,6 +51,9 @@ struct GAMELIST {
|
||||||
GAMELIST ngcd_list[100];
|
GAMELIST ngcd_list[100];
|
||||||
int nListItems = 0;
|
int nListItems = 0;
|
||||||
|
|
||||||
|
// CD image stuff
|
||||||
|
const int nSectorLength = 2352;
|
||||||
|
|
||||||
// Add game to List
|
// Add game to List
|
||||||
static int NeoCDList_AddGame(TCHAR* pszFile, unsigned int nGameID)
|
static int NeoCDList_AddGame(TCHAR* pszFile, unsigned int nGameID)
|
||||||
{
|
{
|
||||||
|
@ -158,7 +161,6 @@ static int NeoCDList_CheckDuplicates(HWND hList, unsigned int nID)
|
||||||
|
|
||||||
static void NeoCDList_iso9660_CheckDirRecord(HWND hList, TCHAR* pszFile, FILE* fp, int nSector)
|
static void NeoCDList_iso9660_CheckDirRecord(HWND hList, TCHAR* pszFile, FILE* fp, int nSector)
|
||||||
{
|
{
|
||||||
int nSectorLength = 2048;
|
|
||||||
//int nFile = 0;
|
//int nFile = 0;
|
||||||
unsigned int lBytesRead = 0;
|
unsigned int lBytesRead = 0;
|
||||||
//int nLen = 0;
|
//int nLen = 0;
|
||||||
|
@ -207,7 +209,7 @@ static void NeoCDList_iso9660_CheckDirRecord(HWND hList, TCHAR* pszFile, FILE*
|
||||||
iso9660_ReadOffset(nLenDR, fp, lOffset + 1, 1, sizeof(unsigned char));
|
iso9660_ReadOffset(nLenDR, fp, lOffset + 1, 1, sizeof(unsigned char));
|
||||||
|
|
||||||
if(nLenDR[0] < 0x22) {
|
if(nLenDR[0] < 0x22) {
|
||||||
lOffset += (2048 - lBytesRead);
|
lOffset += (nSectorLength - lBytesRead);
|
||||||
lBytesRead = 0;
|
lBytesRead = 0;
|
||||||
bNewSector = true;
|
bNewSector = true;
|
||||||
continue;
|
continue;
|
||||||
|
@ -228,7 +230,7 @@ static void NeoCDList_iso9660_CheckDirRecord(HWND hList, TCHAR* pszFile, FILE*
|
||||||
unsigned int nValue = 0;
|
unsigned int nValue = 0;
|
||||||
sscanf(szValue, "%x", &nValue);
|
sscanf(szValue, "%x", &nValue);
|
||||||
|
|
||||||
iso9660_ReadOffset(Data, fp, nValue * 2048, 0x10a, sizeof(unsigned char));
|
iso9660_ReadOffset(Data, fp, nValue * nSectorLength, 0x10a, sizeof(unsigned char));
|
||||||
|
|
||||||
char szData[8];
|
char szData[8];
|
||||||
sprintf(szData, "%c%c%c%c%c%c%c", Data[0x100], Data[0x101], Data[0x102], Data[0x103], Data[0x104], Data[0x105], Data[0x106]);
|
sprintf(szData, "%c%c%c%c%c%c%c", Data[0x100], Data[0x101], Data[0x102], Data[0x103], Data[0x104], Data[0x105], Data[0x106]);
|
||||||
|
@ -249,6 +251,8 @@ static void NeoCDList_iso9660_CheckDirRecord(HWND hList, TCHAR* pszFile, FILE*
|
||||||
strncpy(File, File, LEN_FI[0]);
|
strncpy(File, File, LEN_FI[0]);
|
||||||
File[LEN_FI[0]] = 0;
|
File[LEN_FI[0]] = 0;
|
||||||
|
|
||||||
|
//bprintf(0, _T("\n------------\n--------------> nID %X\n"), nID);
|
||||||
|
|
||||||
// King of Fighters '94, The (1994)(SNK)(JP)
|
// King of Fighters '94, The (1994)(SNK)(JP)
|
||||||
// 10-6-1994 (P1.PRG)
|
// 10-6-1994 (P1.PRG)
|
||||||
if(nID == 0x0055 && Data[0x67] == 0xDE) {
|
if(nID == 0x0055 && Data[0x67] == 0xDE) {
|
||||||
|
@ -353,7 +357,7 @@ static int NeoCDList_CheckISO(HWND hList, TCHAR* pszFile)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Make sure we have a valid ISO file extension...
|
// Make sure we have a valid ISO file extension...
|
||||||
if(_tcsstr(pszFile, _T(".iso")) || _tcsstr(pszFile, _T(".ISO")) )
|
if ( IsFileExt(pszFile, _T(".img")) || IsFileExt(pszFile, _T(".bin")) )
|
||||||
{
|
{
|
||||||
FILE* fp = _tfopen(pszFile, _T("rb"));
|
FILE* fp = _tfopen(pszFile, _T("rb"));
|
||||||
if(fp)
|
if(fp)
|
||||||
|
@ -369,16 +373,15 @@ static int NeoCDList_CheckISO(HWND hList, TCHAR* pszFile)
|
||||||
fseek(fp, 0, SEEK_SET);
|
fseek(fp, 0, SEEK_SET);
|
||||||
|
|
||||||
// If it has at least 16 sectors proceed
|
// If it has at least 16 sectors proceed
|
||||||
if(lSize > (2048 * 16))
|
if(lSize > (nSectorLength * 16))
|
||||||
{
|
{
|
||||||
// Check for Standard ISO9660 Identifier
|
// Check for Standard ISO9660 Identifier
|
||||||
unsigned char IsoHeader[2048 * 16 + 1];
|
|
||||||
unsigned char IsoCheck[6];
|
unsigned char IsoCheck[6];
|
||||||
|
|
||||||
fread(IsoHeader, 1, 2048 * 16 + 1, fp); // advance to sector 16 and PVD Field 2
|
// advance to sector 16 and PVD Field 2
|
||||||
fread(IsoCheck, 1, 5, fp); // get Standard Identifier Field from PVD
|
iso9660_ReadOffset(&IsoCheck[0], fp, 2352 * 16 + 1, 1, 5); // get Standard Identifier Field from PVD
|
||||||
|
|
||||||
// Verify that we have indeed a valid ISO9660 MODE1/2048
|
// Verify that we have indeed a valid ISO9660 MODE1/2352
|
||||||
if(!memcmp(IsoCheck, "CD001", 5))
|
if(!memcmp(IsoCheck, "CD001", 5))
|
||||||
{
|
{
|
||||||
//bprintf(PRINT_NORMAL, _T(" Standard ISO9660 Identifier Found. \n"));
|
//bprintf(PRINT_NORMAL, _T(" Standard ISO9660 Identifier Found. \n"));
|
||||||
|
@ -387,7 +390,7 @@ static int NeoCDList_CheckISO(HWND hList, TCHAR* pszFile)
|
||||||
// Get Volume Descriptor Header
|
// Get Volume Descriptor Header
|
||||||
memset(&vdh, 0, sizeof(vdh));
|
memset(&vdh, 0, sizeof(vdh));
|
||||||
//memcpy(&vdh, iso9660_ReadOffset(fp, (2048 * 16), sizeof(vdh)), sizeof(vdh));
|
//memcpy(&vdh, iso9660_ReadOffset(fp, (2048 * 16), sizeof(vdh)), sizeof(vdh));
|
||||||
iso9660_ReadOffset((unsigned char*)&vdh, fp, 2048 * 16, 1, sizeof(vdh));
|
iso9660_ReadOffset((unsigned char*)&vdh, fp, 16 * 2352, 1, sizeof(vdh));
|
||||||
|
|
||||||
// Check for a valid Volume Descriptor Type
|
// Check for a valid Volume Descriptor Type
|
||||||
if(vdh.vdtype == 0x01)
|
if(vdh.vdtype == 0x01)
|
||||||
|
@ -398,7 +401,7 @@ static int NeoCDList_CheckISO(HWND hList, TCHAR* pszFile)
|
||||||
iso9660_PVD pvd;
|
iso9660_PVD pvd;
|
||||||
memset(&pvd, 0, sizeof(pvd));
|
memset(&pvd, 0, sizeof(pvd));
|
||||||
//memcpy(&pvd, iso9660_ReadOffset(fp, (2048 * 16), sizeof(pvd)), sizeof(pvd));
|
//memcpy(&pvd, iso9660_ReadOffset(fp, (2048 * 16), sizeof(pvd)), sizeof(pvd));
|
||||||
iso9660_ReadOffset((unsigned char*)&pvd, fp, 2048 * 16, 1, sizeof(pvd));
|
iso9660_ReadOffset((unsigned char*)&pvd, fp, 2352 * 16, 1, sizeof(pvd));
|
||||||
|
|
||||||
// ROOT DIRECTORY RECORD
|
// ROOT DIRECTORY RECORD
|
||||||
|
|
||||||
|
@ -415,13 +418,12 @@ static int NeoCDList_CheckISO(HWND hList, TCHAR* pszFile)
|
||||||
// Convert HEX string to Decimal
|
// Convert HEX string to Decimal
|
||||||
sscanf(szRootSector, "%X", &nRootSector);
|
sscanf(szRootSector, "%X", &nRootSector);
|
||||||
#else
|
#else
|
||||||
// Just read from the file directly at the correct offset (0x8000 + 0x9e for the start of the root directory record)
|
// Just read from the file directly at the correct offset (SECTOR_SIZE * 16 + 0x9e for the start of the root directory record)
|
||||||
unsigned char buffer[8];
|
unsigned char buffer[8];
|
||||||
char szRootSector[32];
|
char szRootSector[32];
|
||||||
unsigned int nRootSector = 0;
|
unsigned int nRootSector = 0;
|
||||||
|
|
||||||
fseek(fp, 0x809e, SEEK_SET);
|
iso9660_ReadOffset(&buffer[0], fp, 2352 * 16 + 0x9e, 1, 8);
|
||||||
fread(buffer, 1, 8, fp);
|
|
||||||
|
|
||||||
sprintf(szRootSector, "%02x%02x%02x%02x", buffer[4], buffer[5], buffer[6], buffer[7]);
|
sprintf(szRootSector, "%02x%02x%02x%02x", buffer[4], buffer[5], buffer[6], buffer[7]);
|
||||||
|
|
||||||
|
@ -491,9 +493,6 @@ static void NeoCDList_ScanDir(HWND hList, TCHAR* pszDirectory)
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
TCHAR* pszISO = NULL;
|
|
||||||
pszISO = (TCHAR*)malloc(sizeof(TCHAR) * 512);
|
|
||||||
|
|
||||||
bool bDone = false;
|
bool bDone = false;
|
||||||
|
|
||||||
WIN32_FIND_DATA ffdSubDirectory;
|
WIN32_FIND_DATA ffdSubDirectory;
|
||||||
|
@ -505,7 +504,6 @@ static void NeoCDList_ScanDir(HWND hList, TCHAR* pszDirectory)
|
||||||
|
|
||||||
if(!bNeoCDListScanOnlyISO)
|
if(!bNeoCDListScanOnlyISO)
|
||||||
{
|
{
|
||||||
|
|
||||||
// Scan sub-directory for CUE
|
// Scan sub-directory for CUE
|
||||||
_stprintf(szSubSearch, _T("%s%s/*.cue"), pszDirectory, ffdDirectory.cFileName);
|
_stprintf(szSubSearch, _T("%s%s/*.cue"), pszDirectory, ffdDirectory.cFileName);
|
||||||
|
|
||||||
|
@ -521,18 +519,20 @@ static void NeoCDList_ScanDir(HWND hList, TCHAR* pszDirectory)
|
||||||
if(!(ffdSubDirectory.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY))
|
if(!(ffdSubDirectory.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY))
|
||||||
{
|
{
|
||||||
// File is CUE
|
// File is CUE
|
||||||
if(_tcsstr(ffdSubDirectory.cFileName, _T(".cue")) || _tcsstr(ffdSubDirectory.cFileName, _T(".CUE")))
|
if(IsFileExt(ffdSubDirectory.cFileName, _T(".cue")))
|
||||||
{
|
{
|
||||||
// Parse CUE
|
// Parse CUE
|
||||||
TCHAR szParse[512] = _T("\0");
|
TCHAR szParse[512] = _T("\0");
|
||||||
_stprintf(szParse, _T("%s%s/%s"), pszDirectory, ffdDirectory.cFileName, ffdSubDirectory.cFileName);
|
_stprintf(szParse, _T("%s%s\\%s"), pszDirectory, ffdDirectory.cFileName, ffdSubDirectory.cFileName);
|
||||||
|
|
||||||
//MessageBox(NULL, szParse, _T(""), MB_OK);
|
//MessageBox(NULL, szParse, _T(""), MB_OK);
|
||||||
|
|
||||||
pszISO = NeoCDList_ParseCUE( szParse );
|
TCHAR *pszISO = NeoCDList_ParseCUE( szParse );
|
||||||
|
|
||||||
TCHAR szISO[512] =_T("\0");
|
TCHAR szISO[512] =_T("\0");
|
||||||
_stprintf(szISO, _T("%s%s/%s"), pszDirectory, ffdDirectory.cFileName, pszISO);
|
_stprintf(szISO, _T("%s%s\\%s"), pszDirectory, ffdDirectory.cFileName, pszISO);
|
||||||
|
|
||||||
|
free(pszISO);
|
||||||
|
|
||||||
NeoCDList_CheckISO(hList, szISO);
|
NeoCDList_CheckISO(hList, szISO);
|
||||||
bDone = true;
|
bDone = true;
|
||||||
|
@ -543,11 +543,6 @@ static void NeoCDList_ScanDir(HWND hList, TCHAR* pszDirectory)
|
||||||
} while(FindNextFile(hSubDirectory, &ffdSubDirectory));
|
} while(FindNextFile(hSubDirectory, &ffdSubDirectory));
|
||||||
}
|
}
|
||||||
|
|
||||||
if(pszISO) {
|
|
||||||
free(pszISO);
|
|
||||||
pszISO = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(bDone) {
|
if(bDone) {
|
||||||
FindClose(hSubDirectory);
|
FindClose(hSubDirectory);
|
||||||
continue;
|
continue;
|
||||||
|
@ -562,7 +557,7 @@ static void NeoCDList_ScanDir(HWND hList, TCHAR* pszDirectory)
|
||||||
memset(&ffdSubDirectory, 0, sizeof(WIN32_FIND_DATA));
|
memset(&ffdSubDirectory, 0, sizeof(WIN32_FIND_DATA));
|
||||||
|
|
||||||
// Scan sub-directory for ISO
|
// Scan sub-directory for ISO
|
||||||
_stprintf(szSubSearch, _T("%s%s/*.iso"), pszDirectory, ffdDirectory.cFileName);
|
_stprintf(szSubSearch, _T("%s%s/*.*"), pszDirectory, ffdDirectory.cFileName);
|
||||||
|
|
||||||
hSubDirectory = FindFirstFile(szSubSearch, &ffdSubDirectory);
|
hSubDirectory = FindFirstFile(szSubSearch, &ffdSubDirectory);
|
||||||
|
|
||||||
|
@ -576,10 +571,10 @@ static void NeoCDList_ScanDir(HWND hList, TCHAR* pszDirectory)
|
||||||
if(!(ffdSubDirectory.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY))
|
if(!(ffdSubDirectory.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY))
|
||||||
{
|
{
|
||||||
// File is ISO
|
// File is ISO
|
||||||
if(_tcsstr(ffdSubDirectory.cFileName, _T(".iso")) || _tcsstr(ffdSubDirectory.cFileName, _T(".ISO")))
|
if ( IsFileExt(ffdSubDirectory.cFileName, _T(".img")) || IsFileExt(ffdSubDirectory.cFileName, _T(".bin")) )
|
||||||
{
|
{
|
||||||
TCHAR szISO[512] = _T("\0");
|
TCHAR szISO[512] = _T("\0");
|
||||||
_stprintf(szISO, _T("%s%s/%s"), pszDirectory, ffdDirectory.cFileName, ffdSubDirectory.cFileName);
|
_stprintf(szISO, _T("%s%s\\%s"), pszDirectory, ffdDirectory.cFileName, ffdSubDirectory.cFileName);
|
||||||
|
|
||||||
NeoCDList_CheckISO(hList, szISO);
|
NeoCDList_CheckISO(hList, szISO);
|
||||||
|
|
||||||
|
@ -605,9 +600,6 @@ static void NeoCDList_ScanSingleDir(HWND hList, TCHAR* pszDirectory)
|
||||||
// ListView_DeleteAllItems(hList);
|
// ListView_DeleteAllItems(hList);
|
||||||
|
|
||||||
//
|
//
|
||||||
TCHAR* pszISO = NULL;
|
|
||||||
pszISO = (TCHAR*)malloc(sizeof(TCHAR) * 512);
|
|
||||||
|
|
||||||
WIN32_FIND_DATA ffdDirectory;
|
WIN32_FIND_DATA ffdDirectory;
|
||||||
|
|
||||||
HANDLE hDirectory = NULL;
|
HANDLE hDirectory = NULL;
|
||||||
|
@ -632,7 +624,7 @@ static void NeoCDList_ScanSingleDir(HWND hList, TCHAR* pszDirectory)
|
||||||
if(!(ffdDirectory.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY))
|
if(!(ffdDirectory.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY))
|
||||||
{
|
{
|
||||||
// File is CUE
|
// File is CUE
|
||||||
if(_tcsstr(ffdDirectory.cFileName, _T(".cue")) || _tcsstr(ffdDirectory.cFileName, _T(".CUE")))
|
if(IsFileExt(ffdDirectory.cFileName, _T(".cue")))
|
||||||
{
|
{
|
||||||
// Parse CUE
|
// Parse CUE
|
||||||
TCHAR szParse[512] = _T("\0");
|
TCHAR szParse[512] = _T("\0");
|
||||||
|
@ -640,10 +632,11 @@ static void NeoCDList_ScanSingleDir(HWND hList, TCHAR* pszDirectory)
|
||||||
|
|
||||||
//MessageBox(NULL, szParse, _T(""), MB_OK);
|
//MessageBox(NULL, szParse, _T(""), MB_OK);
|
||||||
|
|
||||||
pszISO = NeoCDList_ParseCUE( szParse );
|
TCHAR *pszISO = NeoCDList_ParseCUE( szParse );
|
||||||
|
|
||||||
TCHAR szISO[512] =_T("\0");
|
TCHAR szISO[512] =_T("\0");
|
||||||
_stprintf(szISO, _T("%s%s"), pszDirectory, pszISO);
|
_stprintf(szISO, _T("%s%s"), pszDirectory, pszISO);
|
||||||
|
free(pszISO);
|
||||||
|
|
||||||
NeoCDList_CheckISO(hList, szISO);
|
NeoCDList_CheckISO(hList, szISO);
|
||||||
}
|
}
|
||||||
|
@ -662,7 +655,7 @@ static void NeoCDList_ScanSingleDir(HWND hList, TCHAR* pszDirectory)
|
||||||
memset(&ffdDirectory, 0, sizeof(WIN32_FIND_DATA));
|
memset(&ffdDirectory, 0, sizeof(WIN32_FIND_DATA));
|
||||||
|
|
||||||
// Scan directory for ISO
|
// Scan directory for ISO
|
||||||
_stprintf(szSearch, _T("%s*.iso"), pszDirectory);
|
_stprintf(szSearch, _T("%s*.*"), pszDirectory);
|
||||||
|
|
||||||
hDirectory = FindFirstFile(szSearch, &ffdDirectory);
|
hDirectory = FindFirstFile(szSearch, &ffdDirectory);
|
||||||
|
|
||||||
|
@ -676,7 +669,7 @@ static void NeoCDList_ScanSingleDir(HWND hList, TCHAR* pszDirectory)
|
||||||
if(!(ffdDirectory.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY))
|
if(!(ffdDirectory.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY))
|
||||||
{
|
{
|
||||||
// File is ISO
|
// File is ISO
|
||||||
if(_tcsstr(ffdDirectory.cFileName, _T(".iso")) || _tcsstr(ffdDirectory.cFileName, _T(".ISO")))
|
if ( IsFileExt(ffdDirectory.cFileName, _T(".img")) || IsFileExt(ffdDirectory.cFileName, _T(".bin")) )
|
||||||
{
|
{
|
||||||
TCHAR szISO[512] = _T("\0");
|
TCHAR szISO[512] = _T("\0");
|
||||||
_stprintf(szISO, _T("%s%s"), pszDirectory, ffdDirectory.cFileName);
|
_stprintf(szISO, _T("%s%s"), pszDirectory, ffdDirectory.cFileName);
|
||||||
|
@ -690,11 +683,6 @@ static void NeoCDList_ScanSingleDir(HWND hList, TCHAR* pszDirectory)
|
||||||
FindClose(hDirectory);
|
FindClose(hDirectory);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pszISO) {
|
|
||||||
free(pszISO);
|
|
||||||
pszISO = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
// bProcessingList = false;
|
// bProcessingList = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -728,11 +716,7 @@ static TCHAR* NeoCDList_ParseCUE(TCHAR* pszFile)
|
||||||
_fgetts(szBuffer, sizeof(szBuffer), fp);
|
_fgetts(szBuffer, sizeof(szBuffer), fp);
|
||||||
|
|
||||||
// terminate string
|
// terminate string
|
||||||
szBuffer[260] = 0;
|
szBuffer[260] = 0; // ????
|
||||||
|
|
||||||
if(!*szBuffer) {
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
int nLength = 0;
|
int nLength = 0;
|
||||||
nLength = _tcslen(szBuffer);
|
nLength = _tcslen(szBuffer);
|
||||||
|
@ -769,7 +753,7 @@ static TCHAR* NeoCDList_ParseCUE(TCHAR* pszFile)
|
||||||
_tcscpy(ngcd_list[nListItems].szISOFile, pStart + 1);
|
_tcscpy(ngcd_list[nListItems].szISOFile, pStart + 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!_tcsncmp(pEnd + 2, _T("WAVE"), 5)) {
|
/*if (!_tcsncmp(pEnd + 2, _T("WAVE"), 5)) {
|
||||||
if(!ngcd_list[nListItems].nAudioTracks) {
|
if(!ngcd_list[nListItems].nAudioTracks) {
|
||||||
ngcd_list[nListItems].nAudioTracks = 0;
|
ngcd_list[nListItems].nAudioTracks = 0;
|
||||||
}
|
}
|
||||||
|
@ -777,7 +761,7 @@ static TCHAR* NeoCDList_ParseCUE(TCHAR* pszFile)
|
||||||
_tcscpy(ngcd_list[nListItems].szTracks[ngcd_list[nListItems].nAudioTracks], pStart + 1);
|
_tcscpy(ngcd_list[nListItems].szTracks[ngcd_list[nListItems].nAudioTracks], pStart + 1);
|
||||||
|
|
||||||
ngcd_list[nListItems].nAudioTracks++;
|
ngcd_list[nListItems].nAudioTracks++;
|
||||||
}
|
} */
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if(fp) fclose(fp);
|
if(fp) fclose(fp);
|
||||||
|
@ -1254,7 +1238,7 @@ static INT_PTR CALLBACK NeoCDList_WndProc(HWND hDlg, UINT Msg, WPARAM wParam, LP
|
||||||
SetFocus(hListView);
|
SetFocus(hListView);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
#if 0
|
||||||
case IDC_NCD_SISO_ONLY_CHECK:
|
case IDC_NCD_SISO_ONLY_CHECK:
|
||||||
{
|
{
|
||||||
if(BST_CHECKED == IsDlgButtonChecked(hDlg, IDC_NCD_SISO_ONLY_CHECK)) {
|
if(BST_CHECKED == IsDlgButtonChecked(hDlg, IDC_NCD_SISO_ONLY_CHECK)) {
|
||||||
|
@ -1271,7 +1255,7 @@ static INT_PTR CALLBACK NeoCDList_WndProc(HWND hDlg, UINT Msg, WPARAM wParam, LP
|
||||||
SetFocus(hListView);
|
SetFocus(hListView);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
case IDC_NCD_CANCEL_BUTTON:
|
case IDC_NCD_CANCEL_BUTTON:
|
||||||
{
|
{
|
||||||
NeoCDList_Clean();
|
NeoCDList_Clean();
|
||||||
|
|
|
@ -1030,7 +1030,7 @@ static void OnCommand(HWND /*hDlg*/, int id, HWND /*hwndCtl*/, UINT codeNotify)
|
||||||
memset(&ofn, 0, sizeof(ofn));
|
memset(&ofn, 0, sizeof(ofn));
|
||||||
ofn.lStructSize = sizeof(ofn);
|
ofn.lStructSize = sizeof(ofn);
|
||||||
ofn.hwndOwner = hScrnWnd;
|
ofn.hwndOwner = hScrnWnd;
|
||||||
ofn.lpstrFile = CDEmuImage;
|
ofn.lpstrFile = StrReplace(CDEmuImage, _T('/'), _T('\\'));
|
||||||
ofn.nMaxFile = MAX_PATH;
|
ofn.nMaxFile = MAX_PATH;
|
||||||
ofn.lpstrTitle = szTitle;
|
ofn.lpstrTitle = szTitle;
|
||||||
ofn.lpstrFilter = szFilter;
|
ofn.lpstrFilter = szFilter;
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
// State dialog module
|
// State dialog module
|
||||||
#include "burner.h"
|
#include "burner.h"
|
||||||
|
#include "neocdlist.h"
|
||||||
|
|
||||||
extern bool bReplayDontClose;
|
extern bool bReplayDontClose;
|
||||||
int bDrvSaveAll = 0;
|
int bDrvSaveAll = 0;
|
||||||
|
@ -27,7 +28,11 @@ int StatedAuto(int bSave)
|
||||||
static TCHAR szName[MAX_PATH] = _T("");
|
static TCHAR szName[MAX_PATH] = _T("");
|
||||||
int nRet;
|
int nRet;
|
||||||
|
|
||||||
|
if (NeoCDInfo_ID()) {
|
||||||
|
_stprintf(szName, _T("config/games/ngcd_%s.fs"), NeoCDInfo_Text(DRV_NAME));
|
||||||
|
} else {
|
||||||
_stprintf(szName, _T("config/games/%s.fs"), BurnDrvGetText(DRV_NAME));
|
_stprintf(szName, _T("config/games/%s.fs"), BurnDrvGetText(DRV_NAME));
|
||||||
|
}
|
||||||
|
|
||||||
if (bSave == 0) {
|
if (bSave == 0) {
|
||||||
nRet = BurnStateLoad(szName, bDrvSaveAll, NULL); // Load ram
|
nRet = BurnStateLoad(szName, bDrvSaveAll, NULL); // Load ram
|
||||||
|
@ -43,7 +48,11 @@ int StatedAuto(int bSave)
|
||||||
|
|
||||||
static void CreateStateName(int nSlot)
|
static void CreateStateName(int nSlot)
|
||||||
{
|
{
|
||||||
|
if (NeoCDInfo_ID()) {
|
||||||
|
_stprintf(szChoice, _T("./savestates/ngcd_%s slot %02x.fs"), NeoCDInfo_Text(DRV_NAME), nSlot);
|
||||||
|
} else {
|
||||||
_stprintf(szChoice, _T("./savestates/%s slot %02x.fs"), BurnDrvGetText(DRV_NAME), nSlot);
|
_stprintf(szChoice, _T("./savestates/%s slot %02x.fs"), BurnDrvGetText(DRV_NAME), nSlot);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int StatedUNDO(int nSlot)
|
int StatedUNDO(int nSlot)
|
||||||
|
@ -78,7 +87,11 @@ int StatedLoad(int nSlot)
|
||||||
CreateStateName(nSlot);
|
CreateStateName(nSlot);
|
||||||
} else {
|
} else {
|
||||||
if (bDrvOkay) {
|
if (bDrvOkay) {
|
||||||
|
if (NeoCDInfo_ID()) {
|
||||||
|
_stprintf(szChoice, _T("ngcd_%s*.fs"), NeoCDInfo_Text(DRV_NAME));
|
||||||
|
} else {
|
||||||
_stprintf(szChoice, _T("%s*.fs"), BurnDrvGetText(DRV_NAME));
|
_stprintf(szChoice, _T("%s*.fs"), BurnDrvGetText(DRV_NAME));
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
_stprintf(szChoice, _T("savestate"));
|
_stprintf(szChoice, _T("savestate"));
|
||||||
}
|
}
|
||||||
|
@ -141,8 +154,12 @@ int StatedSave(int nSlot)
|
||||||
|
|
||||||
if (nSlot) {
|
if (nSlot) {
|
||||||
CreateStateName(nSlot);
|
CreateStateName(nSlot);
|
||||||
|
} else {
|
||||||
|
if (NeoCDInfo_ID()) {
|
||||||
|
_stprintf(szChoice, _T("ngcd_%s"), NeoCDInfo_Text(DRV_NAME));
|
||||||
} else {
|
} else {
|
||||||
_stprintf(szChoice, _T("%s"), BurnDrvGetText(DRV_NAME));
|
_stprintf(szChoice, _T("%s"), BurnDrvGetText(DRV_NAME));
|
||||||
|
}
|
||||||
MakeOfn(szFilter);
|
MakeOfn(szFilter);
|
||||||
ofn.lpstrTitle = FBALoadStringEx(hAppInst, IDS_STATE_SAVE, true);
|
ofn.lpstrTitle = FBALoadStringEx(hAppInst, IDS_STATE_SAVE, true);
|
||||||
ofn.Flags |= OFN_OVERWRITEPROMPT;
|
ofn.Flags |= OFN_OVERWRITEPROMPT;
|
||||||
|
|
|
@ -21,7 +21,8 @@ struct ZetExt {
|
||||||
pZetReadHandler ZetRead;
|
pZetReadHandler ZetRead;
|
||||||
pZetWriteHandler ZetWrite;
|
pZetWriteHandler ZetWrite;
|
||||||
|
|
||||||
UINT8 BusReq;
|
UINT32 BusReq;
|
||||||
|
UINT32 ResetLine;
|
||||||
};
|
};
|
||||||
|
|
||||||
static INT32 nZetCyclesDone[MAX_Z80];
|
static INT32 nZetCyclesDone[MAX_Z80];
|
||||||
|
@ -216,7 +217,8 @@ INT32 ZetInit(INT32 nCPU)
|
||||||
ZetCPUContext[nCPU]->ZetRead = ZetDummyReadHandler;
|
ZetCPUContext[nCPU]->ZetRead = ZetDummyReadHandler;
|
||||||
ZetCPUContext[nCPU]->ZetWrite = ZetDummyWriteHandler;
|
ZetCPUContext[nCPU]->ZetWrite = ZetDummyWriteHandler;
|
||||||
ZetCPUContext[nCPU]->BusReq = 0;
|
ZetCPUContext[nCPU]->BusReq = 0;
|
||||||
// TODO: Z80Init() will set IX IY F regs with default value, so get them ...
|
ZetCPUContext[nCPU]->ResetLine = 0;
|
||||||
|
// Z80Init() will set IX IY F regs with default value, so get them ...
|
||||||
Z80GetContext(&ZetCPUContext[nCPU]->reg);
|
Z80GetContext(&ZetCPUContext[nCPU]->reg);
|
||||||
|
|
||||||
nZetCyclesDone[nCPU] = 0;
|
nZetCyclesDone[nCPU] = 0;
|
||||||
|
@ -265,6 +267,7 @@ INT32 ZetInit(INT32 nCount)
|
||||||
ZetCPUContext[i].ZetRead = ZetDummyReadHandler;
|
ZetCPUContext[i].ZetRead = ZetDummyReadHandler;
|
||||||
ZetCPUContext[i].ZetWrite = ZetDummyWriteHandler;
|
ZetCPUContext[i].ZetWrite = ZetDummyWriteHandler;
|
||||||
ZetCPUContext[i].BusReq = 0;
|
ZetCPUContext[i].BusReq = 0;
|
||||||
|
ZetCPUContext[i].ResetLine = 0;
|
||||||
// TODO: Z80Init() will set IX IY F regs with default value, so get them ...
|
// TODO: Z80Init() will set IX IY F regs with default value, so get them ...
|
||||||
Z80GetContext(&ZetCPUContext[i].reg);
|
Z80GetContext(&ZetCPUContext[i].reg);
|
||||||
|
|
||||||
|
@ -388,13 +391,9 @@ INT32 ZetRun(INT32 nCycles)
|
||||||
nCycles -= nDelayed;
|
nCycles -= nDelayed;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ZetCPUContext[nOpenedCPU]->BusReq) {
|
if (!ZetCPUContext[nOpenedCPU]->BusReq && !ZetCPUContext[nOpenedCPU]->ResetLine) {
|
||||||
nCycles += nDelayed;
|
|
||||||
nZetCyclesTotal += nCycles;
|
|
||||||
return nCycles;
|
|
||||||
}
|
|
||||||
|
|
||||||
nCycles = Z80Execute(nCycles);
|
nCycles = Z80Execute(nCycles);
|
||||||
|
}
|
||||||
|
|
||||||
nCycles += nDelayed;
|
nCycles += nDelayed;
|
||||||
|
|
||||||
|
@ -698,6 +697,7 @@ INT32 ZetScan(INT32 nAction)
|
||||||
SCAN_VAR(nZetCyclesDone[i]);
|
SCAN_VAR(nZetCyclesDone[i]);
|
||||||
SCAN_VAR(nZetCyclesDelayed[i]);
|
SCAN_VAR(nZetCyclesDelayed[i]);
|
||||||
SCAN_VAR(ZetCPUContext[i]->BusReq);
|
SCAN_VAR(ZetCPUContext[i]->BusReq);
|
||||||
|
SCAN_VAR(ZetCPUContext[i]->ResetLine);
|
||||||
}
|
}
|
||||||
|
|
||||||
SCAN_VAR(nZetCyclesTotal);
|
SCAN_VAR(nZetCyclesTotal);
|
||||||
|
@ -821,6 +821,32 @@ INT32 ZetGetBUSREQLine()
|
||||||
return ZetCPUContext[nOpenedCPU]->BusReq;
|
return ZetCPUContext[nOpenedCPU]->BusReq;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ZetSetRESETLine(INT32 nStatus)
|
||||||
|
{
|
||||||
|
#if defined FBA_DEBUG
|
||||||
|
if (!DebugCPU_ZetInitted) bprintf(PRINT_ERROR, _T("ZetSetRESETLine called without init\n"));
|
||||||
|
if (nOpenedCPU == -1) bprintf(PRINT_ERROR, _T("ZetSetRESETLine called when no CPU open\n"));
|
||||||
|
#endif
|
||||||
|
|
||||||
|
if (nOpenedCPU < 0) return;
|
||||||
|
|
||||||
|
if (ZetCPUContext[nOpenedCPU]->ResetLine && nStatus == 0) {
|
||||||
|
ZetReset();
|
||||||
|
}
|
||||||
|
|
||||||
|
ZetCPUContext[nOpenedCPU]->ResetLine = nStatus;
|
||||||
|
}
|
||||||
|
|
||||||
|
INT32 ZetGetRESETLine()
|
||||||
|
{
|
||||||
|
#if defined FBA_DEBUG
|
||||||
|
if (!DebugCPU_ZetInitted) bprintf(PRINT_ERROR, _T("ZetGetRESET called without init\n"));
|
||||||
|
if (nOpenedCPU == -1) bprintf(PRINT_ERROR, _T("ZetGetRESET called when no CPU open\n"));
|
||||||
|
#endif
|
||||||
|
|
||||||
|
return ZetCPUContext[nOpenedCPU]->ResetLine;
|
||||||
|
}
|
||||||
|
|
||||||
void ZetSetAF(INT32 n, UINT16 value)
|
void ZetSetAF(INT32 n, UINT16 value)
|
||||||
{
|
{
|
||||||
ZetCPUContext[n]->reg.af.w.l = value;
|
ZetCPUContext[n]->reg.af.w.l = value;
|
||||||
|
|
|
@ -81,6 +81,9 @@ void ZetSetEDFECallback(void (*pCallback)(Z80_Regs*));
|
||||||
void ZetSetBUSREQLine(INT32 nStatus);
|
void ZetSetBUSREQLine(INT32 nStatus);
|
||||||
INT32 ZetGetBUSREQLine();
|
INT32 ZetGetBUSREQLine();
|
||||||
|
|
||||||
|
void ZetSetRESETLine(INT32 nStatus);
|
||||||
|
INT32 ZetGetRESETLine();
|
||||||
|
|
||||||
void ZetCheatWriteROM(UINT32 a, UINT8 d); // cheat core
|
void ZetCheatWriteROM(UINT32 a, UINT8 d); // cheat core
|
||||||
UINT8 ZetCheatRead(UINT32 a);
|
UINT8 ZetCheatRead(UINT32 a);
|
||||||
|
|
||||||
|
|
|
@ -13,7 +13,7 @@ static InterfaceInfo CDEmuInfo = { NULL, NULL, NULL };
|
||||||
#elif defined BUILD_SDL
|
#elif defined BUILD_SDL
|
||||||
// CD emulation module
|
// CD emulation module
|
||||||
#elif defined (_XBOX)
|
#elif defined (_XBOX)
|
||||||
extern struct CDEmuDo isowavDo;
|
extern struct CDEmuDo cdimgDo;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
static struct CDEmuDo* pCDEmuDo[] =
|
static struct CDEmuDo* pCDEmuDo[] =
|
||||||
|
@ -23,7 +23,7 @@ static struct CDEmuDo* pCDEmuDo[] =
|
||||||
#elif defined BUILD_SDL
|
#elif defined BUILD_SDL
|
||||||
// CD emulation module
|
// CD emulation module
|
||||||
#elif defined (_XBOX)
|
#elif defined (_XBOX)
|
||||||
&isowavDo,
|
&cdimgDo,
|
||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -5,6 +5,7 @@
|
||||||
// CD emulation module
|
// CD emulation module
|
||||||
|
|
||||||
enum CDEmuStatusValue { idle = 0, reading, playing, paused, seeking, fastforward, fastreverse };
|
enum CDEmuStatusValue { idle = 0, reading, playing, paused, seeking, fastforward, fastreverse };
|
||||||
|
enum CDEmuReadTOCFlags { CDEmuTOC_FIRSTLAST = 0x1000, CDEmuTOC_LASTMSF, CDEmuTOC_FIRSTINDEX };
|
||||||
|
|
||||||
extern TCHAR CDEmuImage[MAX_PATH];
|
extern TCHAR CDEmuImage[MAX_PATH];
|
||||||
|
|
||||||
|
|
|
@ -2,7 +2,6 @@
|
||||||
// .bin/.cue re-work by dink
|
// .bin/.cue re-work by dink
|
||||||
|
|
||||||
#include "burner.h"
|
#include "burner.h"
|
||||||
#include "io.h"
|
|
||||||
|
|
||||||
const int MAXIMUM_NUMBER_TRACKS = 100;
|
const int MAXIMUM_NUMBER_TRACKS = 100;
|
||||||
|
|
||||||
|
@ -16,7 +15,6 @@ const int CD_TYPE_CCD = 1 << 2;
|
||||||
static int cd_pregap;
|
static int cd_pregap;
|
||||||
|
|
||||||
struct MSF { UINT8 M; UINT8 S; UINT8 F; };
|
struct MSF { UINT8 M; UINT8 S; UINT8 F; };
|
||||||
struct MSFAddress { UINT8 Control; MSF MSF; };
|
|
||||||
|
|
||||||
struct cdimgTRACK_DATA { UINT8 Control; UINT8 TrackNumber; UINT8 Address[4]; UINT8 EndAddress[4]; };
|
struct cdimgTRACK_DATA { UINT8 Control; UINT8 TrackNumber; UINT8 Address[4]; UINT8 EndAddress[4]; };
|
||||||
struct cdimgCDROM_TOC { UINT8 FirstTrack; UINT8 LastTrack; UINT8 ImageType; TCHAR Image[MAX_PATH]; cdimgTRACK_DATA TrackData[MAXIMUM_NUMBER_TRACKS]; };
|
struct cdimgCDROM_TOC { UINT8 FirstTrack; UINT8 LastTrack; UINT8 ImageType; TCHAR Image[MAX_PATH]; cdimgTRACK_DATA TrackData[MAXIMUM_NUMBER_TRACKS]; };
|
||||||
|
@ -160,6 +158,21 @@ static void cdimgPrintImageInfo()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void cdimgAddLastTrack()
|
||||||
|
{ // Make a fake last-track w/total image size (for bounds checking)
|
||||||
|
FILE* h = _wfopen(cdimgTOC->Image, _T("rb"));
|
||||||
|
if (h)
|
||||||
|
{
|
||||||
|
fseek(h, 0, SEEK_END);
|
||||||
|
const UINT8* address = cdimgLBAToMSF(((ftell(h) + 2351) / 2352) + cd_pregap);
|
||||||
|
fclose(h);
|
||||||
|
|
||||||
|
cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[1] = address[1];
|
||||||
|
cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[2] = address[2];
|
||||||
|
cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[3] = address[3];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// parse .sub file and build a TOC based in Q sub channel data
|
// parse .sub file and build a TOC based in Q sub channel data
|
||||||
static int cdimgParseSubFile()
|
static int cdimgParseSubFile()
|
||||||
{
|
{
|
||||||
|
@ -177,9 +190,9 @@ static int cdimgParseSubFile()
|
||||||
length = _tcslen(filename_sub);
|
length = _tcslen(filename_sub);
|
||||||
|
|
||||||
if (length <= 4 ||
|
if (length <= 4 ||
|
||||||
(_tcscmp(_T(".ccd"), filename_sub + length - 4) &&
|
(!IsFileExt(filename_sub, _T(".ccd")) &&
|
||||||
_tcscmp(_T(".img"), filename_sub + length - 4) &&
|
!IsFileExt(filename_sub, _T(".img")) &&
|
||||||
_tcscmp(_T(".sub"), filename_sub + length - 4)))
|
!IsFileExt(filename_sub, _T(".sub"))))
|
||||||
{
|
{
|
||||||
dprintf(_T("*** Bad image: %s\n"), filename_sub);
|
dprintf(_T("*** Bad image: %s\n"), filename_sub);
|
||||||
return 1;
|
return 1;
|
||||||
|
@ -259,19 +272,7 @@ static int cdimgParseSubFile()
|
||||||
cd_pregap = QChannel[0].MSFabs.F + QChannel[0].MSFabs.S * CD_FRAMES_SECOND + QChannel[0].MSFabs.M * CD_FRAMES_MINUTE;
|
cd_pregap = QChannel[0].MSFabs.F + QChannel[0].MSFabs.S * CD_FRAMES_SECOND + QChannel[0].MSFabs.M * CD_FRAMES_MINUTE;
|
||||||
//bprintf(0, _T("pregap lba: %d MSF: %d:%d:%d\n"), cd_pregap, QChannel[0].MSFabs.M, QChannel[0].MSFabs.S, QChannel[0].MSFabs.F);
|
//bprintf(0, _T("pregap lba: %d MSF: %d:%d:%d\n"), cd_pregap, QChannel[0].MSFabs.M, QChannel[0].MSFabs.S, QChannel[0].MSFabs.F);
|
||||||
|
|
||||||
{ // Make a fake last-track w/total image size (for bounds checking)
|
cdimgAddLastTrack();
|
||||||
h = _wfopen(cdimgTOC->Image, _T("rb"));
|
|
||||||
if (h)
|
|
||||||
{
|
|
||||||
fseek(h, 0, SEEK_END);
|
|
||||||
const UINT8* address = cdimgLBAToMSF((ftell(h) + 2351) / 2352);
|
|
||||||
fclose(h);
|
|
||||||
|
|
||||||
cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[1] = address[1];
|
|
||||||
cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[2] = address[2];
|
|
||||||
cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[3] = address[3];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -331,7 +332,7 @@ static int cdimgParseCueFile()
|
||||||
QuoteRead(&szQuote, NULL, s);
|
QuoteRead(&szQuote, NULL, s);
|
||||||
|
|
||||||
_sntprintf(szFile, ExtractFilename(CDEmuImage) - CDEmuImage, _T("%s"), CDEmuImage);
|
_sntprintf(szFile, ExtractFilename(CDEmuImage) - CDEmuImage, _T("%s"), CDEmuImage);
|
||||||
_sntprintf(szFile + (ExtractFilename(CDEmuImage) - CDEmuImage), 1024 - (ExtractFilename(CDEmuImage) - CDEmuImage), _T("/%s"), szQuote);
|
_sntprintf(szFile + (ExtractFilename(CDEmuImage) - CDEmuImage), 1024 - (ExtractFilename(CDEmuImage) - CDEmuImage), _T("\\%s"), szQuote);
|
||||||
|
|
||||||
if (track == 1) {
|
if (track == 1) {
|
||||||
//bprintf(0, _T("Image file (from .CUE): %s\n"), szFile);
|
//bprintf(0, _T("Image file (from .CUE): %s\n"), szFile);
|
||||||
|
@ -421,19 +422,7 @@ static int cdimgParseCueFile()
|
||||||
|
|
||||||
fclose(h);
|
fclose(h);
|
||||||
|
|
||||||
{
|
cdimgAddLastTrack();
|
||||||
h = _wfopen(cdimgTOC->Image, _T("rb"));
|
|
||||||
if (h)
|
|
||||||
{
|
|
||||||
fseek(h, 0, SEEK_END);
|
|
||||||
const UINT8* address = cdimgLBAToMSF((ftell(h) + 2351) / 2352);
|
|
||||||
fclose(h);
|
|
||||||
|
|
||||||
cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[1] = address[1];
|
|
||||||
cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[2] = address[2];
|
|
||||||
cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[3] = address[3];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -477,7 +466,7 @@ static int cdimgInit()
|
||||||
if (_tcslen(filename) < 4)
|
if (_tcslen(filename) < 4)
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
if (_tcscmp(_T(".cue"), filename + _tcslen(filename) - 4) == 0)
|
if (IsFileExt(filename, _T(".cue")))
|
||||||
{
|
{
|
||||||
if (cdimgParseCueFile())
|
if (cdimgParseCueFile())
|
||||||
{
|
{
|
||||||
|
@ -488,7 +477,7 @@ static int cdimgInit()
|
||||||
}
|
}
|
||||||
|
|
||||||
} else
|
} else
|
||||||
if (_tcscmp(_T(".ccd"), filename + _tcslen(filename) - 4) == 0)
|
if (IsFileExt(filename, _T(".ccd")))
|
||||||
{
|
{
|
||||||
if (cdimgParseSubFile())
|
if (cdimgParseSubFile())
|
||||||
{
|
{
|
||||||
|
@ -615,7 +604,8 @@ static int cdimgPlay(UINT8 M, UINT8 S, UINT8 F)
|
||||||
{
|
{
|
||||||
const UINT8 address[] = { 0, M, S, F };
|
const UINT8 address[] = { 0, M, S, F };
|
||||||
|
|
||||||
dprintf(_T(" play %02i:%02i:%02i\n"), M, S, F);
|
const UINT8* displayaddress = dinkLBAToMSF(cdimgMSFToLBA(address));
|
||||||
|
dprintf(_T(" play %02i:%02i:%02i\n"), displayaddress[1], displayaddress[2], displayaddress[3]);
|
||||||
|
|
||||||
return cdimgPlayLBA(cdimgMSFToLBA(address));
|
return cdimgPlayLBA(cdimgMSFToLBA(address));
|
||||||
}
|
}
|
||||||
|
@ -675,7 +665,7 @@ static UINT8* cdimgReadTOC(int track)
|
||||||
{
|
{
|
||||||
static UINT8 TOCEntry[4];
|
static UINT8 TOCEntry[4];
|
||||||
|
|
||||||
if (track == -1)
|
if (track == CDEmuTOC_FIRSTLAST)
|
||||||
{
|
{
|
||||||
TOCEntry[0] = tobcd(cdimgTOC->FirstTrack - 1);
|
TOCEntry[0] = tobcd(cdimgTOC->FirstTrack - 1);
|
||||||
TOCEntry[1] = tobcd(cdimgTOC->LastTrack);
|
TOCEntry[1] = tobcd(cdimgTOC->LastTrack);
|
||||||
|
@ -684,7 +674,7 @@ static UINT8* cdimgReadTOC(int track)
|
||||||
|
|
||||||
return TOCEntry;
|
return TOCEntry;
|
||||||
}
|
}
|
||||||
if (track == -2)
|
if (track == CDEmuTOC_LASTMSF)
|
||||||
{
|
{
|
||||||
TOCEntry[0] = cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[1];
|
TOCEntry[0] = cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[1];
|
||||||
TOCEntry[1] = cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[2];
|
TOCEntry[1] = cdimgTOC->TrackData[cdimgTOC->LastTrack].Address[2];
|
||||||
|
@ -694,6 +684,21 @@ static UINT8* cdimgReadTOC(int track)
|
||||||
|
|
||||||
return TOCEntry;
|
return TOCEntry;
|
||||||
}
|
}
|
||||||
|
if (track == CDEmuTOC_FIRSTINDEX)
|
||||||
|
{
|
||||||
|
if (cdimgLBA < cdimgMSFToLBA(cdimgTOC->TrackData[cdimgTOC->FirstTrack].Address))
|
||||||
|
{
|
||||||
|
const UINT8* addressUNBCD = dinkLBAToMSF(cdimgLBA);
|
||||||
|
UINT8 index = ((addressUNBCD[1] * 60) + (addressUNBCD[2] + 4)) / 4;
|
||||||
|
TOCEntry[0] = tobcd((index < 100) ? index : 99);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
TOCEntry[0] = tobcd(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
return TOCEntry;
|
||||||
|
}
|
||||||
|
|
||||||
track = bcd(track);
|
track = bcd(track);
|
||||||
if (track >= cdimgTOC->FirstTrack - 1 && track <= cdimgTOC->LastTrack)
|
if (track >= cdimgTOC->FirstTrack - 1 && track <= cdimgTOC->LastTrack)
|
||||||
|
@ -787,6 +792,17 @@ static int cdimgGetSoundBuffer(short* buffer, int samples)
|
||||||
cdimgPlayLBA(cdimgLBA); */
|
cdimgPlayLBA(cdimgLBA); */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
extern int counter;
|
||||||
|
if (counter) {
|
||||||
|
const UINT8* displayaddress = dinkLBAToMSF(cdimgLBA);
|
||||||
|
dprintf(_T(" index %02i:%02i:%02i"), displayaddress[1], displayaddress[2], displayaddress[3]);
|
||||||
|
INT32 endt = cdimgMSFToLBA(cdimgTOC->TrackData[cdimgTrack + 1 /* next track */].Address);
|
||||||
|
const UINT8* displayaddressend = dinkLBAToMSF(endt);
|
||||||
|
dprintf(_T(" end %02i:%02i:%02i\n"), displayaddressend[1], displayaddressend[2], displayaddressend[3]);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
if (cdimgFile == NULL) { // restart play if fileptr lost
|
if (cdimgFile == NULL) { // restart play if fileptr lost
|
||||||
bprintf(0, _T("CDDA file pointer lost, re-starting!\n"));
|
bprintf(0, _T("CDDA file pointer lost, re-starting!\n"));
|
||||||
if (cdimgLBA < cdimgMSFToLBA(cdimgTOC->TrackData[cdimgTrack + 1].Address))
|
if (cdimgLBA < cdimgMSFToLBA(cdimgTOC->TrackData[cdimgTrack + 1].Address))
|
||||||
|
@ -798,6 +814,12 @@ static int cdimgGetSoundBuffer(short* buffer, int samples)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (cdimgLBA >= cdimgMSFToLBA(cdimgTOC->TrackData[cdimgTrack + 1 /* next track */].Address)) {
|
||||||
|
bprintf(0, _T("End of audio track %d reached!! stopping.\n"), cdimgTrack + 1);
|
||||||
|
cdimgStop();
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
if ((cdimgOutputPosition + samples) >= cdimgOutputbufferSize)
|
if ((cdimgOutputPosition + samples) >= cdimgOutputbufferSize)
|
||||||
{
|
{
|
||||||
short* src = cdimgOutputbuffer + cdimgOutputPosition * 2;
|
short* src = cdimgOutputbuffer + cdimgOutputPosition * 2;
|
||||||
|
@ -813,14 +835,8 @@ static int cdimgGetSoundBuffer(short* buffer, int samples)
|
||||||
samples -= (cdimgOutputbufferSize - cdimgOutputPosition);
|
samples -= (cdimgOutputbufferSize - cdimgOutputPosition);
|
||||||
|
|
||||||
cdimgOutputPosition = 0;
|
cdimgOutputPosition = 0;
|
||||||
cdimgLBA++;
|
|
||||||
if ((cdimgOutputbufferSize = fread(cdimgOutputbuffer, 4, cdimgOUT_SIZE, cdimgFile)) <= 0)
|
if ((cdimgOutputbufferSize = fread(cdimgOutputbuffer, 4, cdimgOUT_SIZE, cdimgFile)) <= 0)
|
||||||
cdimgStop();
|
cdimgStop();
|
||||||
|
|
||||||
if (cdimgLBA >= cdimgMSFToLBA(cdimgTOC->TrackData[cdimgTrack + 1 /* next track */].Address)) {
|
|
||||||
bprintf(0, _T("End of audio track %d reached!! stopping.\n"), cdimgTrack + 1);
|
|
||||||
cdimgStop();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((cdimgOutputPosition + samples) < cdimgOutputbufferSize)
|
if ((cdimgOutputPosition + samples) < cdimgOutputbufferSize)
|
||||||
|
|
|
@ -1,595 +0,0 @@
|
||||||
// ----------------------------------------------------------------------------
|
|
||||||
// iso/cue/wav support
|
|
||||||
/*-----------------------------------------------------------------------------
|
|
||||||
Modified by: CaptainCPS-X
|
|
||||||
Updates:
|
|
||||||
(10/24/2011)
|
|
||||||
- removed libmad and MP3 support
|
|
||||||
- added my custom DirectSound library to add WAV support
|
|
||||||
- removed most (if not all) references to MP3
|
|
||||||
- modified a few other things as needed
|
|
||||||
------------------------------------------------------------------------------*/
|
|
||||||
#include "burner.h"
|
|
||||||
#include "cdsound.h"
|
|
||||||
|
|
||||||
#define MAXIMUM_NUMBER_TRACKS (100)
|
|
||||||
|
|
||||||
#define CD_FRAMES_MINUTE (60 * 75)
|
|
||||||
#define CD_FRAMES_SECOND ( 75)
|
|
||||||
#define CD_FRAMES_PREGAP ( 2 * 75)
|
|
||||||
|
|
||||||
struct isowavTRACK_DATA {
|
|
||||||
char Control;
|
|
||||||
char TrackNumber;
|
|
||||||
char Address[4];
|
|
||||||
TCHAR* Filename;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct isowavCDROM_TOC {
|
|
||||||
char FirstTrack;
|
|
||||||
char LastTrack;
|
|
||||||
isowavTRACK_DATA TrackData[MAXIMUM_NUMBER_TRACKS];
|
|
||||||
};
|
|
||||||
|
|
||||||
static isowavCDROM_TOC* isowavTOC;
|
|
||||||
|
|
||||||
static FILE* isowavFile = NULL;
|
|
||||||
static int isowavTrack = 0;
|
|
||||||
static int isowavLBA = 0;
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
static const char* isowavLBAToMSF(const int LBA)
|
|
||||||
{
|
|
||||||
static char address[4];
|
|
||||||
|
|
||||||
address[0] = 0;
|
|
||||||
address[1] = LBA / CD_FRAMES_MINUTE;
|
|
||||||
address[2] = LBA % CD_FRAMES_MINUTE / CD_FRAMES_SECOND;
|
|
||||||
address[3] = LBA % CD_FRAMES_SECOND;
|
|
||||||
|
|
||||||
return address;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int isowavMSFToLBA(const char* address)
|
|
||||||
{
|
|
||||||
int LBA;
|
|
||||||
|
|
||||||
LBA = address[3];
|
|
||||||
LBA += address[2] * CD_FRAMES_SECOND;
|
|
||||||
LBA += address[1] * CD_FRAMES_MINUTE;
|
|
||||||
|
|
||||||
return LBA;
|
|
||||||
}
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
static int isowavGetTrackSizes()
|
|
||||||
{
|
|
||||||
// determine the lenght of the .iso / .mp3 files to complete the TOC
|
|
||||||
|
|
||||||
FILE* h;
|
|
||||||
|
|
||||||
for (int i = isowavTOC->FirstTrack - 1; i < isowavTOC->LastTrack; i++) {
|
|
||||||
|
|
||||||
const char* address;
|
|
||||||
|
|
||||||
if (isowavTOC->TrackData[i].Control & 4) {
|
|
||||||
|
|
||||||
// data track
|
|
||||||
|
|
||||||
h = _tfopen(isowavTOC->TrackData[i].Filename, _T("rb"));
|
|
||||||
if (h == NULL) return 1;
|
|
||||||
|
|
||||||
fseek(h, 0, SEEK_END);
|
|
||||||
|
|
||||||
address = isowavLBAToMSF((ftell(h) + 2047) / 2048 + isowavMSFToLBA(isowavTOC->TrackData[i].Address));
|
|
||||||
|
|
||||||
if(h) fclose(h);
|
|
||||||
|
|
||||||
} else {
|
|
||||||
|
|
||||||
// audio track
|
|
||||||
|
|
||||||
h = _tfopen(isowavTOC->TrackData[i].Filename, _T("rb"));
|
|
||||||
if (h == NULL)return 1;
|
|
||||||
|
|
||||||
fseek(h, 0, SEEK_END);
|
|
||||||
|
|
||||||
address = isowavLBAToMSF(((ftell(h) + 2047) / 2048) + isowavMSFToLBA(isowavTOC->TrackData[i].Address));
|
|
||||||
if(h) fclose(h);
|
|
||||||
}
|
|
||||||
|
|
||||||
isowavTOC->TrackData[i + 1].Address[0] += 0; // always 0 [?]
|
|
||||||
isowavTOC->TrackData[i + 1].Address[1] += address[1]; // M
|
|
||||||
isowavTOC->TrackData[i + 1].Address[2] += address[2]; // S
|
|
||||||
isowavTOC->TrackData[i + 1].Address[3] += address[3]; // F
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int isowavTestISO()
|
|
||||||
{
|
|
||||||
TCHAR fullname[MAX_PATH];
|
|
||||||
TCHAR* filename;
|
|
||||||
int length = 0;
|
|
||||||
int offset = 0;
|
|
||||||
int track = 2;
|
|
||||||
FILE* h;
|
|
||||||
|
|
||||||
_tcscpy(fullname, CDEmuImage);
|
|
||||||
length = _tcslen(fullname);
|
|
||||||
|
|
||||||
// assume CD-ROM mode1/2048 format
|
|
||||||
|
|
||||||
if (length <= 4 && (_tcscmp(_T(".iso"), fullname + length - 4) || _tcscmp(_T(".bin"), fullname + length - 4))) {
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
// create a TOC with only the data track first
|
|
||||||
|
|
||||||
isowavTOC->FirstTrack = 1;
|
|
||||||
isowavTOC->LastTrack = 1;
|
|
||||||
|
|
||||||
isowavTOC->TrackData[0].TrackNumber = 1;
|
|
||||||
|
|
||||||
isowavTOC->TrackData[0].Address[1] = 0;
|
|
||||||
isowavTOC->TrackData[0].Address[2] = 2;
|
|
||||||
isowavTOC->TrackData[0].Address[3] = 0;
|
|
||||||
|
|
||||||
isowavTOC->TrackData[0].Filename = (TCHAR*)malloc((length + 1) * sizeof(TCHAR));
|
|
||||||
if (isowavTOC->TrackData[0].Filename == NULL) {
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
_tcscpy(isowavTOC->TrackData[0].Filename, fullname);
|
|
||||||
|
|
||||||
isowavTOC->TrackData[0].Control = 4;
|
|
||||||
|
|
||||||
// if the filename has a number in it, try to find .mp3 tracks
|
|
||||||
|
|
||||||
filename = ExtractFilename(fullname);
|
|
||||||
offset = (filename - fullname) + length - 6;
|
|
||||||
while (offset >= 0 && fullname[offset] != _T('0') && fullname[offset + 1] != _T('1')) {
|
|
||||||
offset--;
|
|
||||||
}
|
|
||||||
if (offset < 0) {
|
|
||||||
return isowavGetTrackSizes();
|
|
||||||
}
|
|
||||||
|
|
||||||
_stprintf(fullname + length - 4, _T(".wav"));
|
|
||||||
|
|
||||||
while (1) {
|
|
||||||
fullname[offset] = _T('0') + track / 10; fullname[offset + 1] = _T('0') + track % 10;
|
|
||||||
|
|
||||||
if ((h = _tfopen(fullname, _T("rb"))) == NULL) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
fclose(h);
|
|
||||||
|
|
||||||
isowavTOC->TrackData[track - 1].TrackNumber = track;
|
|
||||||
|
|
||||||
isowavTOC->TrackData[track - 1].Filename = (TCHAR*)malloc((length + 1) * sizeof(TCHAR));
|
|
||||||
if (isowavTOC->TrackData[track - 1].Filename == NULL) {
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
_tcscpy(isowavTOC->TrackData[track - 1].Filename, fullname);
|
|
||||||
|
|
||||||
isowavTOC->LastTrack = track;
|
|
||||||
|
|
||||||
track++;
|
|
||||||
}
|
|
||||||
|
|
||||||
return isowavGetTrackSizes();
|
|
||||||
}
|
|
||||||
|
|
||||||
static int isowavParseCueFile()
|
|
||||||
{
|
|
||||||
TCHAR szLine[1024];
|
|
||||||
TCHAR szFile[1024];
|
|
||||||
TCHAR* s;
|
|
||||||
TCHAR* t;
|
|
||||||
FILE* h;
|
|
||||||
int track = 0;
|
|
||||||
int length;
|
|
||||||
|
|
||||||
isowavTOC->FirstTrack = 1;
|
|
||||||
isowavTOC->LastTrack = 1;
|
|
||||||
|
|
||||||
isowavTOC->TrackData[0].Address[1] = 0;
|
|
||||||
isowavTOC->TrackData[0].Address[2] = 2;
|
|
||||||
isowavTOC->TrackData[0].Address[3] = 0;
|
|
||||||
|
|
||||||
h = _tfopen(CDEmuImage, _T("rt"));
|
|
||||||
if (h == NULL) {
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
while (1) {
|
|
||||||
if (_fgetts(szLine, sizeof(szLine), h) == NULL) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
length = _tcslen(szLine);
|
|
||||||
// get rid of the linefeed at the end
|
|
||||||
while (length && (szLine[length - 1] == _T('\r') || szLine[length - 1] == _T('\n'))) {
|
|
||||||
szLine[length - 1] = 0;
|
|
||||||
length--;
|
|
||||||
}
|
|
||||||
|
|
||||||
s = szLine;
|
|
||||||
|
|
||||||
// file info
|
|
||||||
if ((t = LabelCheck(s, _T("FILE"))) != 0) {
|
|
||||||
s = t;
|
|
||||||
|
|
||||||
TCHAR* szQuote;
|
|
||||||
|
|
||||||
// read filename
|
|
||||||
QuoteRead(&szQuote, NULL, s);
|
|
||||||
|
|
||||||
_sntprintf(szFile, ExtractFilename(CDEmuImage) - CDEmuImage, _T("%s"), CDEmuImage);
|
|
||||||
_sntprintf(szFile + (ExtractFilename(CDEmuImage) - CDEmuImage), 1024 - (ExtractFilename(CDEmuImage) - CDEmuImage), _T("/%s"), szQuote);
|
|
||||||
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
// track info
|
|
||||||
if ((t = LabelCheck(s, _T("TRACK"))) != 0) {
|
|
||||||
s = t;
|
|
||||||
|
|
||||||
// track number
|
|
||||||
track = _tcstol(s, &t, 10);
|
|
||||||
|
|
||||||
if (track < 1 || track > MAXIMUM_NUMBER_TRACKS) {
|
|
||||||
fclose(h);
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (track < isowavTOC->FirstTrack) {
|
|
||||||
isowavTOC->FirstTrack = track;
|
|
||||||
}
|
|
||||||
if (track > isowavTOC->LastTrack) {
|
|
||||||
isowavTOC->LastTrack = track;
|
|
||||||
}
|
|
||||||
isowavTOC->TrackData[track - 1].TrackNumber = track;
|
|
||||||
|
|
||||||
isowavTOC->TrackData[track - 1].Filename = (TCHAR*)malloc((_tcslen(szFile) + 1) * sizeof(TCHAR));
|
|
||||||
if (isowavTOC->TrackData[track - 1].Filename == NULL) {
|
|
||||||
fclose(h);
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
_tcscpy(isowavTOC->TrackData[track - 1].Filename, szFile);
|
|
||||||
|
|
||||||
s = t;
|
|
||||||
|
|
||||||
// type of track
|
|
||||||
|
|
||||||
if ((t = LabelCheck(s, _T("MODE1/2048"))) != 0) {
|
|
||||||
isowavTOC->TrackData[track - 1].Control = 4;
|
|
||||||
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if ((t = LabelCheck(s, _T("AUDIO"))) != 0) {
|
|
||||||
isowavTOC->TrackData[track - 1].Control = 0;
|
|
||||||
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
fclose(h);
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
// pregap
|
|
||||||
if ((t = LabelCheck(s, _T("PREGAP"))) != 0) {
|
|
||||||
s = t;
|
|
||||||
|
|
||||||
int M, S, F;
|
|
||||||
|
|
||||||
// pregap M
|
|
||||||
M = _tcstol(s, &t, 10);
|
|
||||||
s = t + 1;
|
|
||||||
// pregap S
|
|
||||||
S = _tcstol(s, &t, 10);
|
|
||||||
s = t + 1;
|
|
||||||
// pregap F
|
|
||||||
F = _tcstol(s, &t, 10);
|
|
||||||
|
|
||||||
if (M < 0 || M > 100 || S < 0 || S > 59 || F < 0 || F > 74) {
|
|
||||||
fclose(h);
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
isowavTOC->TrackData[track - 1].Address[1] = M;
|
|
||||||
isowavTOC->TrackData[track - 1].Address[2] = S;
|
|
||||||
isowavTOC->TrackData[track - 1].Address[3] = F;
|
|
||||||
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fclose(h);
|
|
||||||
|
|
||||||
return isowavGetTrackSizes();
|
|
||||||
}
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
static int isowavExit()
|
|
||||||
{
|
|
||||||
wav_exit();
|
|
||||||
|
|
||||||
if (isowavFile) {
|
|
||||||
fclose(isowavFile);
|
|
||||||
isowavFile = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
isowavTrack = 0;
|
|
||||||
isowavLBA = 0;
|
|
||||||
|
|
||||||
if (isowavTOC) {
|
|
||||||
for (int i = 0; i < MAXIMUM_NUMBER_TRACKS; i++) {
|
|
||||||
free(isowavTOC->TrackData[i].Filename);
|
|
||||||
}
|
|
||||||
|
|
||||||
free(isowavTOC);
|
|
||||||
isowavTOC = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int isowavInit()
|
|
||||||
{
|
|
||||||
wav_exit();
|
|
||||||
|
|
||||||
isowavTOC = (isowavCDROM_TOC*)malloc(sizeof(isowavCDROM_TOC));
|
|
||||||
if (isowavTOC == NULL) {
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
memset(isowavTOC, 0, sizeof(isowavCDROM_TOC));
|
|
||||||
|
|
||||||
TCHAR* filename = ExtractFilename(CDEmuImage);
|
|
||||||
|
|
||||||
if (_tcslen(filename) < 4) {
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (_tcscmp(_T(".cue"), filename + _tcslen(filename) - 4) == 0) {
|
|
||||||
if (isowavParseCueFile()) {
|
|
||||||
dprintf(_T("*** Couldn't parse .cue file\n"));
|
|
||||||
isowavExit();
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (isowavTestISO()) {
|
|
||||||
dprintf(_T("*** Couldn't find .iso / .bin file\n"));
|
|
||||||
isowavExit();
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
dprintf(_T(" CD image TOC read\n"));
|
|
||||||
|
|
||||||
for (int i = isowavTOC->FirstTrack - 1; i < isowavTOC->LastTrack; i++) {
|
|
||||||
dprintf(_T(" track %2i start %02i:%02i:%02i control 0x%02X %s\n"), isowavTOC->TrackData[i].TrackNumber, isowavTOC->TrackData[i].Address[1], isowavTOC->TrackData[i].Address[2], isowavTOC->TrackData[i].Address[3], isowavTOC->TrackData[i].Control, isowavTOC->TrackData[i].Filename);
|
|
||||||
}
|
|
||||||
dprintf(_T(" total running time %02i:%02i:%02i\n"), isowavTOC->TrackData[(int)isowavTOC->LastTrack].Address[1], isowavTOC->TrackData[(int)isowavTOC->LastTrack].Address[2], isowavTOC->TrackData[(int)isowavTOC->LastTrack].Address[3]);
|
|
||||||
|
|
||||||
CDEmuStatus = idle;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
TCHAR* GetIsoPath()
|
|
||||||
{
|
|
||||||
if(isowavTOC) {
|
|
||||||
return isowavTOC->TrackData[0].Filename;
|
|
||||||
}
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int isowavStop()
|
|
||||||
{
|
|
||||||
wav_stop();
|
|
||||||
|
|
||||||
if (isowavFile) {
|
|
||||||
fclose(isowavFile);
|
|
||||||
isowavFile = NULL;
|
|
||||||
}
|
|
||||||
CDEmuStatus = idle;
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int isowavPlayLBA(int LBA)
|
|
||||||
{
|
|
||||||
isowavLBA = LBA;
|
|
||||||
|
|
||||||
for (isowavTrack = isowavTOC->FirstTrack - 1; isowavTrack < isowavTOC->LastTrack; isowavTrack++) {
|
|
||||||
if (isowavLBA < isowavMSFToLBA(isowavTOC->TrackData[isowavTrack + 1].Address)) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (isowavTrack >= isowavTOC->LastTrack) {
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
bprintf(PRINT_IMPORTANT, _T(" playing track %2i - %s\n"), isowavTrack + 1, isowavTOC->TrackData[isowavTrack].Filename);
|
|
||||||
|
|
||||||
isowavFile = _tfopen(isowavTOC->TrackData[isowavTrack].Filename, _T("rb"));
|
|
||||||
if (isowavFile == NULL) {
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if( _tcsstr(isowavTOC->TrackData[isowavTrack].Filename, _T(".wav")) || _tcsstr(isowavTOC->TrackData[isowavTrack].Filename, _T(".WAV"))) {
|
|
||||||
// is a wav, no need to keep this file pointer
|
|
||||||
if (isowavFile) {
|
|
||||||
fclose(isowavFile);
|
|
||||||
isowavFile = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(wav_open(isowavTOC->TrackData[isowavTrack].Filename)) {
|
|
||||||
wav_play();
|
|
||||||
} else {
|
|
||||||
// error creating the WAV stream
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//dprintf(_T("*** WAV: wBitsPerSample: %d \n"), wav->g_pStreamingSound->m_pWaveFile->m_pwfx->wBitsPerSample);
|
|
||||||
//dprintf(_T("*** WAV: nAvgBytesPerSec: %d \n"), wav->g_pStreamingSound->m_pWaveFile->m_pwfx->nAvgBytesPerSec);
|
|
||||||
//dprintf(_T("*** WAV: m_dwSize: %d \n"), wav->g_pStreamingSound->m_pWaveFile->m_dwSize);
|
|
||||||
//dprintf(_T("*** WAV: nBlockAlign: %d \n"), wav->g_pStreamingSound->m_pWaveFile->m_pwfx->nBlockAlign);
|
|
||||||
|
|
||||||
isowavLBA = isowavMSFToLBA(isowavTOC->TrackData[isowavTrack].Address);
|
|
||||||
CDEmuStatus = playing;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int isowavPlay(unsigned char M, unsigned char S, unsigned char F)
|
|
||||||
{
|
|
||||||
const char address[] = { 0, M, S, F };
|
|
||||||
|
|
||||||
return isowavPlayLBA(isowavMSFToLBA(address));
|
|
||||||
}
|
|
||||||
|
|
||||||
static int isowavLoadSector(int LBA, char* pBuffer)
|
|
||||||
{
|
|
||||||
LBA += CD_FRAMES_PREGAP;
|
|
||||||
|
|
||||||
if (LBA != isowavLBA) {
|
|
||||||
|
|
||||||
int track;
|
|
||||||
|
|
||||||
for (track = isowavTOC->FirstTrack - 1; track < isowavTOC->LastTrack; track++) {
|
|
||||||
if (LBA < isowavMSFToLBA(isowavTOC->TrackData[track + 1].Address)) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (isowavFile == NULL || track != isowavTrack) {
|
|
||||||
isowavStop();
|
|
||||||
|
|
||||||
isowavTrack = track;
|
|
||||||
|
|
||||||
bprintf(PRINT_IMPORTANT, _T(" reading track %2i - %s\n"), isowavTrack + 1, isowavTOC->TrackData[isowavTrack].Filename);
|
|
||||||
|
|
||||||
isowavFile = _tfopen(isowavTOC->TrackData[isowavTrack].Filename, _T("rb"));
|
|
||||||
if (isowavFile == NULL) {
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (fseek(isowavFile, (LBA - isowavMSFToLBA(isowavTOC->TrackData[isowavTrack].Address)) * 2048, SEEK_SET)) {
|
|
||||||
dprintf(_T("*** couldn't seek\n"));
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
isowavLBA = (ftell(isowavFile) + 2047) / 2048;
|
|
||||||
|
|
||||||
CDEmuStatus = reading;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (fread(pBuffer, 1, 2048, isowavFile) <= 0) {
|
|
||||||
dprintf(_T("*** couldn't read from file\n"));
|
|
||||||
|
|
||||||
isowavStop();
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
isowavLBA = isowavMSFToLBA(isowavTOC->TrackData[isowavTrack].Address) + (ftell(isowavFile) + 2047) / 2048;
|
|
||||||
|
|
||||||
return isowavLBA - CD_FRAMES_PREGAP;
|
|
||||||
}
|
|
||||||
|
|
||||||
static unsigned char* isowavReadTOC(int track)
|
|
||||||
{
|
|
||||||
static unsigned char TOCEntry[4];
|
|
||||||
|
|
||||||
if (track == -1) {
|
|
||||||
TOCEntry[0] = isowavTOC->FirstTrack - 1;
|
|
||||||
TOCEntry[1] = isowavTOC->LastTrack;
|
|
||||||
TOCEntry[2] = 0;
|
|
||||||
TOCEntry[3] = 0;
|
|
||||||
|
|
||||||
return TOCEntry;
|
|
||||||
}
|
|
||||||
if (track == -2) {
|
|
||||||
TOCEntry[0] = isowavTOC->TrackData[(int)isowavTOC->LastTrack].Address[1];
|
|
||||||
TOCEntry[1] = isowavTOC->TrackData[(int)isowavTOC->LastTrack].Address[2];
|
|
||||||
TOCEntry[2] = isowavTOC->TrackData[(int)isowavTOC->LastTrack].Address[3];
|
|
||||||
|
|
||||||
TOCEntry[3] = 0;
|
|
||||||
|
|
||||||
return TOCEntry;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (track >= isowavTOC->FirstTrack - 1 && track <= isowavTOC->LastTrack) {
|
|
||||||
TOCEntry[0] = isowavTOC->TrackData[track - 1].Address[1];
|
|
||||||
TOCEntry[1] = isowavTOC->TrackData[track - 1].Address[2];
|
|
||||||
TOCEntry[2] = isowavTOC->TrackData[track - 1].Address[3];
|
|
||||||
TOCEntry[3] = isowavTOC->TrackData[track - 1].Control;
|
|
||||||
}
|
|
||||||
|
|
||||||
return TOCEntry;
|
|
||||||
}
|
|
||||||
|
|
||||||
static unsigned char* isowavReadQChannel()
|
|
||||||
{
|
|
||||||
static unsigned char QChannelData[8];
|
|
||||||
|
|
||||||
switch (CDEmuStatus) {
|
|
||||||
case reading:
|
|
||||||
case playing: {
|
|
||||||
const char* AddressAbs = isowavLBAToMSF(isowavLBA);
|
|
||||||
const char* AddressRel = isowavLBAToMSF(isowavLBA - isowavMSFToLBA(isowavTOC->TrackData[isowavTrack].Address));
|
|
||||||
|
|
||||||
QChannelData[0] = isowavTOC->TrackData[isowavTrack].TrackNumber;
|
|
||||||
|
|
||||||
QChannelData[1] = AddressAbs[1];
|
|
||||||
QChannelData[2] = AddressAbs[2];
|
|
||||||
QChannelData[3] = AddressAbs[3];
|
|
||||||
|
|
||||||
QChannelData[4] = AddressRel[1];
|
|
||||||
QChannelData[5] = AddressRel[2];
|
|
||||||
QChannelData[6] = AddressRel[3];
|
|
||||||
|
|
||||||
QChannelData[7] = isowavTOC->TrackData[isowavTrack].Control;
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
case paused: {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
default: {
|
|
||||||
memset(QChannelData, 0, sizeof(QChannelData));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return QChannelData;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int isowavGetSoundBuffer(short* /*buffer*/, int /*samples*/)
|
|
||||||
{
|
|
||||||
// ---------------------------------------------------------------------
|
|
||||||
// TODO:
|
|
||||||
// Port the old 'isomp3GetSoundBuffer()' function from 'cd_isomp3.cpp'
|
|
||||||
// to use WAVE stream data, porting that function will fix the
|
|
||||||
// 00:00 progress status on the main NeoGeo CD BIOS menu.
|
|
||||||
// ---------------------------------------------------------------------
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int isowavGetSettings(InterfaceInfo* /*pInfo*/)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
struct CDEmuDo isowavDo = { isowavExit, isowavInit, isowavStop, isowavPlay, isowavLoadSector, isowavReadTOC, isowavReadQChannel, isowavGetSoundBuffer, isowavGetSettings, _T("cue/iso/wav CD emulation") };
|
|
|
@ -1,433 +0,0 @@
|
||||||
#include "burner.h"
|
|
||||||
#include "cdsound.h"
|
|
||||||
|
|
||||||
WavClass::WavClass()
|
|
||||||
{
|
|
||||||
m_DirectSound = 0;
|
|
||||||
m_primaryBuffer = 0;
|
|
||||||
m_secondaryBuffer1 = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
WavClass::WavClass(const WavClass&)
|
|
||||||
{
|
|
||||||
//
|
|
||||||
}
|
|
||||||
|
|
||||||
WavClass::~WavClass()
|
|
||||||
{
|
|
||||||
//
|
|
||||||
}
|
|
||||||
|
|
||||||
bool WavClass::Initialize(HWND hwnd, TCHAR* szFile)
|
|
||||||
{
|
|
||||||
bool result;
|
|
||||||
|
|
||||||
// Initialize direct sound and the primary sound buffer.
|
|
||||||
result = InitializeDirectSound(hwnd);
|
|
||||||
if(!result)
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Load a wave audio file onto a secondary buffer.
|
|
||||||
result = LoadWaveFile(szFile, &m_secondaryBuffer1);
|
|
||||||
if(!result)
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void WavClass::Shutdown()
|
|
||||||
{
|
|
||||||
// Release the secondary buffer.
|
|
||||||
ShutdownWaveFile(&m_secondaryBuffer1);
|
|
||||||
|
|
||||||
// Shutdown the Direct Sound API.
|
|
||||||
ShutdownDirectSound();
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool WavClass::InitializeDirectSound(HWND hwnd)
|
|
||||||
{
|
|
||||||
HRESULT result;
|
|
||||||
DSBUFFERDESC bufferDesc;
|
|
||||||
WAVEFORMATEX waveFormat;
|
|
||||||
|
|
||||||
// Initialize the direct sound interface pointer for the default sound device.
|
|
||||||
result = _DirectSoundCreate(NULL, &m_DirectSound, NULL);
|
|
||||||
if(FAILED(result))
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Set the cooperative level to priority so the format of the primary sound buffer can be modified.
|
|
||||||
result = m_DirectSound->SetCooperativeLevel(hwnd, DSSCL_PRIORITY);
|
|
||||||
if(FAILED(result))
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
GUID guidNULL;
|
|
||||||
memset(&guidNULL,0,sizeof(GUID));
|
|
||||||
|
|
||||||
// Setup the primary buffer description.
|
|
||||||
bufferDesc.dwSize = sizeof(DSBUFFERDESC);
|
|
||||||
bufferDesc.dwFlags = DSBCAPS_PRIMARYBUFFER | DSBCAPS_CTRLVOLUME;
|
|
||||||
bufferDesc.dwBufferBytes = 0;
|
|
||||||
bufferDesc.dwReserved = 0;
|
|
||||||
bufferDesc.lpwfxFormat = NULL;
|
|
||||||
bufferDesc.guid3DAlgorithm = guidNULL; //GUID_NULL;
|
|
||||||
|
|
||||||
// Get control of the primary sound buffer on the default sound device.
|
|
||||||
result = m_DirectSound->CreateSoundBuffer(&bufferDesc, &m_primaryBuffer, NULL);
|
|
||||||
if(FAILED(result))
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Setup the format of the primary sound bufffer.
|
|
||||||
// In this case it is a .WAV file recorded at 44,100 samples per second in 16-bit stereo (cd audio format).
|
|
||||||
waveFormat.wFormatTag = WAVE_FORMAT_PCM;
|
|
||||||
waveFormat.nSamplesPerSec = 44100;
|
|
||||||
waveFormat.wBitsPerSample = 16;
|
|
||||||
waveFormat.nChannels = 2;
|
|
||||||
waveFormat.nBlockAlign = (waveFormat.wBitsPerSample / 8) * waveFormat.nChannels;
|
|
||||||
waveFormat.nAvgBytesPerSec = waveFormat.nSamplesPerSec * waveFormat.nBlockAlign;
|
|
||||||
waveFormat.cbSize = 0;
|
|
||||||
|
|
||||||
// Set the primary buffer to be the wave format specified.
|
|
||||||
result = m_primaryBuffer->SetFormat(&waveFormat);
|
|
||||||
if(FAILED(result))
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void WavClass::ShutdownDirectSound()
|
|
||||||
{
|
|
||||||
// Release the primary sound buffer pointer.
|
|
||||||
if(m_primaryBuffer)
|
|
||||||
{
|
|
||||||
m_primaryBuffer->Release();
|
|
||||||
m_primaryBuffer = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Release the direct sound interface pointer.
|
|
||||||
if(m_DirectSound)
|
|
||||||
{
|
|
||||||
m_DirectSound->Release();
|
|
||||||
m_DirectSound = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool WavClass::LoadWaveFile(TCHAR* filename, IDirectSoundBuffer** secondaryBuffer)
|
|
||||||
{
|
|
||||||
FILE* filePtr;
|
|
||||||
unsigned int count;
|
|
||||||
WaveHeaderType waveFileHeader;
|
|
||||||
WAVEFORMATEX waveFormat;
|
|
||||||
DSBUFFERDESC bufferDesc;
|
|
||||||
HRESULT result;
|
|
||||||
IDirectSoundBuffer* tempBuffer;
|
|
||||||
unsigned char* waveData;
|
|
||||||
unsigned char* bufferPtr;
|
|
||||||
unsigned long bufferSize;
|
|
||||||
|
|
||||||
|
|
||||||
// Open the wave file in binary.
|
|
||||||
filePtr = _tfopen(filename, _T("rb"));
|
|
||||||
if(!filePtr)
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Read in the wave file header.
|
|
||||||
count = fread(&waveFileHeader, sizeof(waveFileHeader), 1, filePtr);
|
|
||||||
if(count != 1)
|
|
||||||
{
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check that the chunk ID is the RIFF format.
|
|
||||||
if((waveFileHeader.chunkId[0] != 'R') || (waveFileHeader.chunkId[1] != 'I') ||
|
|
||||||
(waveFileHeader.chunkId[2] != 'F') || (waveFileHeader.chunkId[3] != 'F'))
|
|
||||||
{
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check that the file format is the WAVE format.
|
|
||||||
if((waveFileHeader.format[0] != 'W') || (waveFileHeader.format[1] != 'A') ||
|
|
||||||
(waveFileHeader.format[2] != 'V') || (waveFileHeader.format[3] != 'E'))
|
|
||||||
{
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check that the sub chunk ID is the fmt format.
|
|
||||||
if((waveFileHeader.subChunkId[0] != 'f') || (waveFileHeader.subChunkId[1] != 'm') ||
|
|
||||||
(waveFileHeader.subChunkId[2] != 't') || (waveFileHeader.subChunkId[3] != ' '))
|
|
||||||
{
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check that the audio format is WAVE_FORMAT_PCM.
|
|
||||||
if(waveFileHeader.audioFormat != WAVE_FORMAT_PCM)
|
|
||||||
{
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check that the wave file was recorded in stereo format.
|
|
||||||
if(waveFileHeader.numChannels != 2)
|
|
||||||
{
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check that the wave file was recorded at a sample rate of 44.1 KHz.
|
|
||||||
if(waveFileHeader.sampleRate != 44100)
|
|
||||||
{
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Ensure that the wave file was recorded in 16 bit format.
|
|
||||||
if(waveFileHeader.bitsPerSample != 16)
|
|
||||||
{
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Check for the data chunk header.
|
|
||||||
if((waveFileHeader.dataChunkId[0] != 'd') || (waveFileHeader.dataChunkId[1] != 'a') ||
|
|
||||||
(waveFileHeader.dataChunkId[2] != 't') || (waveFileHeader.dataChunkId[3] != 'a'))
|
|
||||||
{
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Set the wave format of secondary buffer that this wave file will be loaded onto.
|
|
||||||
waveFormat.wFormatTag = WAVE_FORMAT_PCM;
|
|
||||||
waveFormat.nSamplesPerSec = 44100;
|
|
||||||
waveFormat.wBitsPerSample = 16;
|
|
||||||
waveFormat.nChannels = 2;
|
|
||||||
waveFormat.nBlockAlign = (waveFormat.wBitsPerSample / 8) * waveFormat.nChannels;
|
|
||||||
waveFormat.nAvgBytesPerSec = waveFormat.nSamplesPerSec * waveFormat.nBlockAlign;
|
|
||||||
waveFormat.cbSize = 0;
|
|
||||||
|
|
||||||
GUID guidNULL;
|
|
||||||
memset(&guidNULL,0,sizeof(GUID));
|
|
||||||
|
|
||||||
// Set the buffer description of the secondary sound buffer that the wave file will be loaded onto.
|
|
||||||
bufferDesc.dwSize = sizeof(DSBUFFERDESC);
|
|
||||||
bufferDesc.dwFlags = DSBCAPS_GLOBALFOCUS | DSBCAPS_CTRLPOSITIONNOTIFY | DSBCAPS_GETCURRENTPOSITION2 | DSBCAPS_CTRLVOLUME | DSBCAPS_CTRLPAN | DSBCAPS_CTRLFREQUENCY;
|
|
||||||
bufferDesc.dwBufferBytes = waveFileHeader.dataSize;
|
|
||||||
bufferDesc.dwReserved = 0;
|
|
||||||
bufferDesc.lpwfxFormat = &waveFormat;
|
|
||||||
bufferDesc.guid3DAlgorithm = guidNULL; //GUID_NULL;
|
|
||||||
|
|
||||||
// Create a temporary sound buffer with the specific buffer settings.
|
|
||||||
result = m_DirectSound->CreateSoundBuffer(&bufferDesc, &tempBuffer, NULL);
|
|
||||||
if(FAILED(result))
|
|
||||||
{
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Test the buffer format against the direct sound 8 interface and create the secondary buffer.
|
|
||||||
result = tempBuffer->QueryInterface(IID_IDirectSoundBuffer, (void**)&*secondaryBuffer);
|
|
||||||
if(FAILED(result))
|
|
||||||
{
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Release the temporary buffer.
|
|
||||||
tempBuffer->Release();
|
|
||||||
tempBuffer = 0;
|
|
||||||
|
|
||||||
// Move to the beginning of the wave data which starts at the end of the data chunk header.
|
|
||||||
fseek(filePtr, sizeof(WaveHeaderType), SEEK_SET);
|
|
||||||
|
|
||||||
// Create a temporary buffer to hold the wave file data.
|
|
||||||
waveData = new unsigned char[waveFileHeader.dataSize];
|
|
||||||
if(!waveData)
|
|
||||||
{
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Read in the wave file data into the newly created buffer.
|
|
||||||
count = fread(waveData, 1, waveFileHeader.dataSize, filePtr);
|
|
||||||
if(count != waveFileHeader.dataSize)
|
|
||||||
{
|
|
||||||
delete [] waveData;
|
|
||||||
waveData = 0;
|
|
||||||
|
|
||||||
fclose(filePtr);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Close the file once done reading.
|
|
||||||
int error = fclose(filePtr);
|
|
||||||
if(error != 0)
|
|
||||||
{
|
|
||||||
delete [] waveData;
|
|
||||||
waveData = 0;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Lock the secondary buffer to write wave data into it.
|
|
||||||
result = (*secondaryBuffer)->Lock(0, waveFileHeader.dataSize, (void**)&bufferPtr, (DWORD*)&bufferSize, NULL, 0, 0);
|
|
||||||
if(FAILED(result))
|
|
||||||
{
|
|
||||||
delete [] waveData;
|
|
||||||
waveData = 0;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Copy the wave data into the buffer.
|
|
||||||
memcpy(bufferPtr, waveData, waveFileHeader.dataSize);
|
|
||||||
|
|
||||||
// Unlock the secondary buffer after the data has been written to it.
|
|
||||||
result = (*secondaryBuffer)->Unlock((void*)bufferPtr, bufferSize, NULL, 0);
|
|
||||||
if(FAILED(result))
|
|
||||||
{
|
|
||||||
delete [] waveData;
|
|
||||||
waveData = 0;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Release the wave data since it was copied into the secondary buffer.
|
|
||||||
delete [] waveData;
|
|
||||||
waveData = 0;
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void WavClass::ShutdownWaveFile(IDirectSoundBuffer** secondaryBuffer)
|
|
||||||
{
|
|
||||||
// Release the secondary sound buffer.
|
|
||||||
if(*secondaryBuffer)
|
|
||||||
{
|
|
||||||
(*secondaryBuffer)->Release();
|
|
||||||
*secondaryBuffer = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
#include "cd_interface.h"
|
|
||||||
|
|
||||||
WavClass* wav;
|
|
||||||
extern HWND hScrnWnd;
|
|
||||||
|
|
||||||
void wav_exit()
|
|
||||||
{
|
|
||||||
if(wav) {
|
|
||||||
wav_stop();
|
|
||||||
wav->Shutdown();
|
|
||||||
wav = NULL;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int wav_open(TCHAR* szFile)
|
|
||||||
{
|
|
||||||
wav_exit();
|
|
||||||
|
|
||||||
if(hScrnWnd) {
|
|
||||||
wav = new WavClass;
|
|
||||||
wav->Initialize(hScrnWnd, szFile);
|
|
||||||
} else {
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
void wav_stop()
|
|
||||||
{
|
|
||||||
if(!wav) return;
|
|
||||||
|
|
||||||
wav->GetSecondaryBuffer()->Stop();
|
|
||||||
wav->GetSecondaryBuffer()->SetCurrentPosition( 0 );
|
|
||||||
}
|
|
||||||
|
|
||||||
void wav_play()
|
|
||||||
{
|
|
||||||
if(!wav) return;
|
|
||||||
|
|
||||||
HRESULT result;
|
|
||||||
|
|
||||||
// Play the contents of the secondary sound buffer.
|
|
||||||
IDirectSoundBuffer* m_secondaryBuffer1 = wav->GetSecondaryBuffer();
|
|
||||||
if(!m_secondaryBuffer1) {
|
|
||||||
//
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Set volume of the buffer to 100%.
|
|
||||||
result = m_secondaryBuffer1->SetVolume(DSBVOLUME_MAX);
|
|
||||||
if(FAILED(result))
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
result = m_secondaryBuffer1->Play(0, 0, DSBPLAY_LOOPING);
|
|
||||||
if(FAILED(result)) {
|
|
||||||
//
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void wav_pause(bool bResume)
|
|
||||||
{
|
|
||||||
if(!wav) return;
|
|
||||||
|
|
||||||
if(!bResume)
|
|
||||||
{
|
|
||||||
DWORD pdwStatus;
|
|
||||||
wav->GetSecondaryBuffer()->GetStatus(&pdwStatus);
|
|
||||||
if((pdwStatus & DSBSTATUS_PLAYING) == DSBSTATUS_PLAYING)
|
|
||||||
{
|
|
||||||
HRESULT result;
|
|
||||||
result = wav->GetSecondaryBuffer()->Stop();
|
|
||||||
if(FAILED(result)) {
|
|
||||||
//
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
} else {
|
|
||||||
DWORD pdwStatus;
|
|
||||||
wav->GetSecondaryBuffer()->GetStatus(&pdwStatus);
|
|
||||||
if((pdwStatus & DSBSTATUS_PLAYING) != DSBSTATUS_PLAYING)
|
|
||||||
{
|
|
||||||
if(CDEmuGetStatus() == playing)
|
|
||||||
{
|
|
||||||
HRESULT result;
|
|
||||||
|
|
||||||
// Set volume of the buffer to 100%.
|
|
||||||
result = wav->GetSecondaryBuffer()->SetVolume(DSBVOLUME_MAX);
|
|
||||||
if(FAILED(result))
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
result = wav->GetSecondaryBuffer()->Play(0, 0, DSBPLAY_LOOPING);
|
|
||||||
if(FAILED(result)) {
|
|
||||||
//
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,59 +0,0 @@
|
||||||
#ifndef _WavClass_H_
|
|
||||||
#define _WavClass_H_
|
|
||||||
|
|
||||||
//#include <dsound.h>
|
|
||||||
#include "dsound_core.h"
|
|
||||||
|
|
||||||
class WavClass
|
|
||||||
{
|
|
||||||
private:
|
|
||||||
struct WaveHeaderType
|
|
||||||
{
|
|
||||||
char chunkId[4];
|
|
||||||
unsigned long chunkSize;
|
|
||||||
char format[4];
|
|
||||||
char subChunkId[4];
|
|
||||||
unsigned long subChunkSize;
|
|
||||||
unsigned short audioFormat;
|
|
||||||
unsigned short numChannels;
|
|
||||||
unsigned long sampleRate;
|
|
||||||
unsigned long bytesPerSecond;
|
|
||||||
unsigned short blockAlign;
|
|
||||||
unsigned short bitsPerSample;
|
|
||||||
char dataChunkId[4];
|
|
||||||
unsigned long dataSize;
|
|
||||||
};
|
|
||||||
|
|
||||||
public:
|
|
||||||
WavClass();
|
|
||||||
WavClass(const WavClass&);
|
|
||||||
~WavClass();
|
|
||||||
|
|
||||||
bool Initialize(HWND, TCHAR*);
|
|
||||||
void Shutdown();
|
|
||||||
|
|
||||||
bool InitializeDirectSound(HWND);
|
|
||||||
void ShutdownDirectSound();
|
|
||||||
|
|
||||||
bool LoadWaveFile(TCHAR*, IDirectSoundBuffer**);
|
|
||||||
void ShutdownWaveFile(IDirectSoundBuffer**);
|
|
||||||
|
|
||||||
bool PlayWaveFile();
|
|
||||||
|
|
||||||
IDirectSound* GetDirectSound() { return m_DirectSound; }
|
|
||||||
IDirectSoundBuffer* GetPrimaryBuffer() { return m_primaryBuffer; }
|
|
||||||
IDirectSoundBuffer* GetSecondaryBuffer() { return m_secondaryBuffer1; }
|
|
||||||
|
|
||||||
private:
|
|
||||||
IDirectSound* m_DirectSound;
|
|
||||||
IDirectSoundBuffer* m_primaryBuffer;
|
|
||||||
IDirectSoundBuffer* m_secondaryBuffer1;
|
|
||||||
};
|
|
||||||
|
|
||||||
void wav_exit();
|
|
||||||
int wav_open(TCHAR* szFile);
|
|
||||||
void wav_stop();
|
|
||||||
void wav_play();
|
|
||||||
void wav_pause(bool bResume);
|
|
||||||
|
|
||||||
#endif
|
|
|
@ -301,6 +301,23 @@
|
||||||
<li>Dragonball Z/Dragonball Z 2, impliment sprite dma - fixes missing/flickering sprites & text, fix service mode (F2) [dink]</li>
|
<li>Dragonball Z/Dragonball Z 2, impliment sprite dma - fixes missing/flickering sprites & text, fix service mode (F2) [dink]</li>
|
||||||
<li>Updated Gauntlet protection, game can now progress past level 28 [iq_132]</li>
|
<li>Updated Gauntlet protection, game can now progress past level 28 [iq_132]</li>
|
||||||
<li>Finished Carnival (Vic Dual WIP) - fix bugs / add sound [dink]</li>
|
<li>Finished Carnival (Vic Dual WIP) - fix bugs / add sound [dink]</li>
|
||||||
|
<li>Neo Geo CD gets dink-style upgrade/fix/rework<ul>
|
||||||
|
<li>DAO .bin/cue and TruRip (.ccd/.sub/.img [based on Jan Klaassen's work]) support added</li>
|
||||||
|
<li>Seamless per-game savestates</li>
|
||||||
|
<li>S.S.RPG and Double Dragon works now</li>
|
||||||
|
<li>Fast loading times (even faster with F1/ffwd)</li>
|
||||||
|
<li>Dozens of bugs fixed</li>
|
||||||
|
<li>Convert your old-style Neo Geo CD .iso + .wav's to .bin/.cue, <a href="http://neo-source.com/index.php?topic=2487.msg26465#msg26465"> <b>>> click for howto <<</b> </a></li>
|
||||||
|
<li>Big thanks to Silanda and barbudreadmon for bug reports, ideas, talks and HW tests</li>
|
||||||
|
</ul></li>
|
||||||
|
<li>Added clone of Fantasy Zone to the Sega System 16A driver [Barry]</li>
|
||||||
|
<li>Sync romsets with MAME 0.206 [Barry]</li>
|
||||||
|
<li>Add Kof '98 Plus Final Edition (kof98pfe) & Kof 10th Anniversary (kof10thd) hacks to Neo Geo [barbudreadmon]</li>
|
||||||
|
<li>Added driver for Incredible Technologies 32/16bit games [iq_132, dink]</li>
|
||||||
|
<li>Hook up analog dials for Pachinko Sexy Reaction 1 & 2 [dink]</li>
|
||||||
|
<li>Fix crash issue with Tecmo Bowl when playing via Keyboard [dink]</li>
|
||||||
|
<li>Add RESET Line to Z80 cpu interface [dink]</li>
|
||||||
|
<li> []</li>
|
||||||
<li> []</li>
|
<li> []</li>
|
||||||
</ul>
|
</ul>
|
||||||
<!-- new drivers -->
|
<!-- new drivers -->
|
||||||
|
|
Loading…
Reference in New Issue