|
本帖最后由 william 于 2025-9-25 23:27 编辑
本来是在做fbneo_libretro 增加对nebula格式支持的事,程序写完后,调试过程,发现一些romdata不能运行,就找原因,钻进了源代码的深渊..可能发现了一些问题,也可能不是问题,记录下来,也许对程序编写者或者romdata编写者有参考作用。
记录1:
问题现象:加载游戏时候提示 m0600.rom 文件缺失
romdata 如下:
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
System: PGM
RomName: kovqxzbwss1
Game: 三国战纪 群雄争霸无双版 孙悟空
Parent: kovshpd3dw
[Program]
qxzb_v500cn.rom,0,800000,0,0
[Tile]
t0600.rom,0,800000,0,0
[SpriteData]
a0600.rom,0,800000,0,0
a0601.rom,0,800000,0,0
a0602.rom,0,800000,0,0
a0540.rom,0,800000,0,0
a0541.rom,0,800000,0,0
a0542.rom,0,800000,0,0
a0543.rom,0,800000,0,0
[SpriteMasks]
b0600.rom,0,800000,0,0
b0540.rom,0,800000,0,0
b0541.rom,0,800000,0,0
[Samples]
m0600.rom,0,800000,0,0
[InternalARM7]
qxzb_v100_china.asic,0,8000,0,0
[ExternalARM7]
[System]
AsicRegionHackAddress:
Arm7SetIdleLoopAddress:
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
驱动文件定义如下:
static struct BurnRomInfo kovshpd3dwRomDesc[] = {
{ "kovshpd3dw_p0600.rom", 0x0400000, 0xf88f4b0a, 1 | BRF_PRG | BRF_ESS }, // 0 68K Code
{ "kovshpd3dw_t0600.rom", 0x0800000, 0x1f78d522, 2 | BRF_GRA }, // 1 Tile data
{ "kovshpd3dw_a0600.rom", 0x0800000, 0x72643288, 3 | BRF_GRA }, // 2 Sprite Color Data
{ "kovshpd3dw_a0601.rom", 0x0800000, 0x94a0c63d, 3 | BRF_GRA }, // 3
{ "kovshpd3dw_a0602.rom", 0x0800000, 0xaf21456c, 3 | BRF_GRA }, // 4
{ "kovshpd3dw_a0540.rom", 0x0800000, 0xa3204d56, 3 | BRF_GRA }, // 5
{ "kovshpd3dw_a0541.rom", 0x0800000, 0xfac5160e, 3 | BRF_GRA }, // 6
{ "kovshpd3dw_b0600.rom", 0x0800000, 0x0646c5ef, 4 | BRF_GRA }, // 7 Sprite Masks & Color Indexes
{ "kovshpd3dw_b0540.rom", 0x0800000, 0x8697ec72, 4 | BRF_GRA }, // 8
{ "kovshpd3dw_b0601.rom", 0x0400000, 0xa0bb1c2f, 4 | BRF_GRA }, // 9
{ "kovshpd3dw_m0600.rom", 0x0400000, 0xec3f335d, 5 | BRF_SND }, // 10 Samples
{ "kovshpd3dw_v100_china.asic", 0x0004000, 0xd9a43086, 7 | BRF_PRG | BRF_ESS }, // 11 Internal ARM7 Rom
};
程序对rom状态的设置代码是:
程序先用crc找文件,找不到index就是-1,进入下面这个判断语句的处理中,用名字找文件。下面的代码是我对源码有一些修改(蓝色部分是我增加或者修改的),调试用的,标红的部分是设置rom文件状态值的,程序文件如果和驱动定义中大小不一样,就会被置为3(小于标准),4(大于标准),而只有设置为1(ok)和5(skip),后面才会认为是找到并且是正常的。
if (index < 0)
{
if ((g_find_list_path[z].ignoreCrc && bPatchedRomsetsEnabled) ||
((NULL != pDataRomDesc) && (-1 != pRDI->nDescCount))) // romdata mode
{
uint32_t real_rom_crc;
int name_index = find_rom_by_name(rom_name, list, count, &real_rom_crc); // 使用局部变量,变量名有替换,用局部变量,避免对index的干扰,毕竟原来代码我不熟悉,我用自己更容易把握的方式调试
HandleMessage(RETRO_LOG_DEBUG, "ROMDATA Mode===>[FBNeo] find_rom_by_name returned name_index=%d, count=%d\n", name_index, count);
//用名字找到rom文件后的处理
if (name_index >= 0)
{
unknown_crc = true;
HandleMessage(RETRO_LOG_WARN, "ROMDATA Mode===>[FBNeo] Using ROM with unknown crc 0x%08x and name %s from archive %s\n", real_rom_crc, rom_name, g_find_list_path[z].path.c_str());
//以下红色部分都是我增加的代码,含义是如果是romdata模式,在通过名字找到rom文件后,要设置文件的状态,避免后面被再度检查
// ROM处理代码
if (bIsNeogeoCartGame)
set_neogeo_bios_availability(list[name_index].szName, list[name_index].nCrc, (g_find_list_path[z].ignoreCrc && bPatchedRomsetsEnabled));
pRomFind.nZip = z;
pRomFind.nPos = name_index;
pRomFind.nState = STAT_OK;
if (list[name_index].nLen < ri.nLen)
pRomFind.nState = STAT_SMALL;
else if (list[name_index].nLen > ri.nLen)
pRomFind.nState = STAT_LARGE;
continue;
}
}
}
这个问题很明显,romdata中音频文件的定义800000超过了驱动文件的定义400000,在程序处理的复查过程中
//复查前,增加对state的检查
HandleMessage(RETRO_LOG_DEBUG, "[FBNeo] Pre-check ROM states:\n");
for (unsigned j = 0; j < nRomCount; j++) {
struct BurnRomInfo ri;
BurnDrvGetRomInfo(&ri, j);
char* rom_name_check;
BurnDrvGetRomName(&rom_name_check, j, 0);
HandleMessage(RETRO_LOG_DEBUG, "[FBNeo] ROM %d (%s): state=%d, crc=0x%08x\n", j, rom_name_check, pRomFind[j].nState, ri.nCrc);
}
// Going over every rom to see if they are properly loaded before we continue ...
bool ret = true;
for (unsigned i = 0; i < nRomCount; i++)
{
// Neither the available roms nor the unneeded ones should trigger an error here
// 修改复检逻辑:STAT_OK、STAT_SMALL、STAT_LARGE都认为是找到的
if (pRomFind.nState != STAT_OK &&
pRomFind.nState != STAT_SMALL &&
pRomFind.nState != STAT_LARGE &&
pRomFind.nState != STAT_SKIP)
{
struct BurnRomInfo ri;
memset(&ri, 0, sizeof(ri));
BurnDrvGetRomInfo(&ri, i);
if(!(ri.nType & BRF_OPT))
{
static char prev[2048];
strcpy(prev, text_missing_files);
BurnDrvGetRomName(&rom_name, i, 0);
sprintf(text_missing_files, RETRO_ERROR_MESSAGES_11, prev, rom_name, ri.nCrc);
log_cb(RETRO_LOG_ERROR, "[FBNeo] ROM at index %d with name %s and CRC 0x%08x is required\n", i, rom_name, ri.nCrc);
ret = false;
}
}
}
修改代码运行程序,从前端的日志可以看到如下:
[CORE DEBUG]: [FBNeo] Pre-check ROM states:
[CORE DEBUG]: [FBNeo] ROM 0 (qxzb_v500cn.rom): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 1 (t0600.rom): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 2 (a0600.rom): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 3 (a0601.rom): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 4 (a0602.rom): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 5 (a0540.rom): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 6 (a0541.rom): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 7 (a0542.rom): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 8 (a0543.rom): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 9 (b0600.rom): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 10 (b0540.rom): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 11 (b0541.rom): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 12 (m0600.rom): state=4, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 13 (qxzb_v100_china.asic): state=1, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 14 (): state=5, crc=0x00000000
[CORE DEBUG]: [FBNeo] ROM 15 (): state=5, crc=0x00000000
增加state的检查后,发现值是4,是大于驱动的定义,源代码是等于1(ok)或者5(skip)才算通过,4算缺失,上面是我在复查代码判断条件那里增加了对状态3,4的通过,但这个romdata不争气啊,这样改代码让他通过后,可以加载游戏,但过了启动画面后,不能正常运行,然后我又去改了驱动中这个samples类型的rom文件大小的定义,改为800000,可以加载游戏,还是不能正常运行。对于romdata制作者来说,要注意文件大小要和驱动定义的一致,否则复查这里无法通过的,会被置为3,或者4,显示这个文件缺失,不能加载游戏。
这是rom状态的定义
#define STAT_NOFIND 0
#define STAT_OK 1
#define STAT_CRC 2
#define STAT_SMALL 3
#define STAT_LARGE 4
#define STAT_SKIP 5
查清这个问题根因,代价是3-4个小时....
附1.调试环境说明:自编前端程序EzMAME,加载修改代码后编译的fbneo_libretro.dll ,通过环境回调中的日志接口,观察核心的运行状态和输出,在核心的代码中调用前端的回调函数(核心已封装)来实现。如果需要前端程序的带控制台调试窗口的版本,可以单独编译提供
附2.nebula格式的romdata支持,已经基本实现,现在在做更多的测试,以消除增加代码的可能潜在问题,并提高健壮性。
附3.做这个的出发点,是尽可能的增加对各种改版文件的支持,让历史沉淀下来的东西不至于随风而散,还能发挥一些作用,增加玩家对改版游戏的体验。个人认为,支持romdata是fbneo对模拟器界的巨大贡献,让rom有了一定的发展空间,模拟游戏的生命力得到进一步的延伸。
|
|