主题 : [转贴]RomData编写深入剖析
此人已死。。。
级别: 论坛版主

UID: 264
精华: 0
发帖: 14884
威望: 30 星
金钱: 608944 浮游币
贡献值: 8846 点
好评度: 14697 点
人气: 1736 点
在线时间: 1688(时)
注册时间: 2004-03-25
最后登录: 2022-12-26
楼主  发表于: 2004-05-14 12:45

[转贴]RomData编写深入剖析

最近因为编写软件的关系需要了解模拟器RomData的编写方法,也上网找到一些文章,但不是讲的不明确就是根本不对,所冶ΡΥ下了这篇文章以便大家参考借鉴。由于Capcom CPS1游戏已经全部dump下来了,RomData也已经全部被KO了,而且CPS1游戏的设置开关太多所以本文主要分析SNK MVS游戏和Capcom CPS2游戏的RomData编写方法。
首先让我们来了解一下RomData的基本概念。 (这里指的RomData并不是针对某个模拟器专用的,而是泛指所有模拟器用的RomData)。
什么是RomData?
RomData是一组数据,它有规律的指导模拟器如何对Rom进行加载配置。
没有RomData行不行(单Rom的家用机除外,像GBA)?
答案是可以,但是模拟器也无法识别任何Rom游戏。
到现在为止RomData包括内置和外置两种,而Nebula是最具代表性的,它同时包含了内置和外置两种RomData。我们以Nabule为例来深入了解外置RomData的编写。SNK MVS游戏以The King of Fighters 2002 (Fully Decrypted)的RomData为例,Capcom CPS2游戏以Street Fighter Alpha 3 (US 980904) 的RomData为例。由于SNK MVS游戏与Capcom CPS2游戏RomData的头部System、RomName、Game部分和尾部的System段相似,所以一起放到最后讲。先是以The King of Fighters 2002 (Fully Decrypted)的RomData为例分析SNK MVS游戏RomData的写法。
%%%%%%%%%%%%%Create by RomData Maker%%%%%%%%%%%%%% //注释以%开头,模拟器不会读取

System: NEO //游戏系统,可以是NEO,CPS1,CPS2
RomName: kof2k2nd //游戏的ROM名称,就是Zip包文件名
Game: The King of Fighters 2002 (Fully Decrypted) //游戏名称,可以任意,随个人喜好:-)
[Program] //程序段,配置游戏的程序文件

[Text] //文本段,有的游戏可以没有

[Z80] //大名鼎鼎的Z80 Rom,主管声音

[Samples] //声音取样,存放像枪声之类的声音

[Graphics] //图形Rom,有加密和非加密两种

[System] //系统设置,对模拟器进行配置
CartridgeID: 267 //游戏发行号,MVS游戏是保存在P1Rom中的
GfxCrypt: 0 //游戏用的解密XOR表
GfxKey: 0 //XOR表的初始值
ButLayout: 9 //输出方式
Fix: 0
//修正方式


程序段的写法
[Program]
kof2k2_p1.rom,0,100000,CB49DE80,0
kof2k2_p2.rom,100000,400000,432FDF53,0

第一部分“kof2k2_p1.rom”是文件名,第二部分“0”是基地址,第三部分“100000”是文件大小,第四部分“CB49DE80”是文件Crc校验码,第五部分“0”不明,写0即可,也有写1的,像战国传承3。文件名、文件大小和Crc校验码可以直接用Winzip之类的解压缩软件取得,不过注意文件大小是16进制的。文本段、Z80段、采样段和图形段的写法和程序段都是相同的,所以后面便不再解释了。最麻烦的是基地址的算法,每一段都不同,而且Neo游戏和Capcom游戏也不一样,后面我会详述的。
程序段最重要也是最麻烦的一段。第一个文件的基地址为0,第二个文件的基地址是第一个文件的大小加第一个文件的基地址,第三个文件的基地址是第二个文件的大小加第二个文件的基地址,依此类推。还以上面的为例,Kof2k2_p1.rom由于是第一个文件所以它的基地址为0, kof2k2_p2.rom是第二个文件它的基地址由kof2k2_p1.rom的文件大小加kof2k2_p1.rom的基地址,也就是100000 + 0 = 100000,所以kof2k2_p2.rom的基地址是100000。如果还有kof2k2_p3.rom,它的基地址便是kof2k2_p2.rom的文件大小(400000)加kof2k2_p2.rom的基地址(100000) = 500000。上面只是一种情况,还有一种情况便是程序文件只有一个而且文件大小为200000(2M)那它的基地址便是100000。除了上面说的几种情况以外还有一些情况,由于比较少见就不再一一列举了。
文本段的写法[Text]
kof2k2_s1.rom,0,20000,E0EAABA3,0

文件只有一个,基地址永远都是0。
Z80段的写法[Z80]
kof2k2_m1.rom,0,20000,F80EB346,0

与文本段一样文件只有一个,基地址永远都是0。
声音采样段的写法[Samples]
kof2K2_v1.rom,0,400000,13D98607,0
kof2K2_v2.rom,400000,400000,9CF74677,0
kof2K2_v3.rom,800000,400000,8E9448B5,0
kof2K2_v4.rom,C00000,400000,67271B5,0
与程序段相同只需将基地址与文件大小一一累加便可。
图形段的写法[Graphics]
kof2k2_c1.rom,0,800000,7EFA6EF7,0
kof2k2_c2.rom,1,800000,AA82948B,0
kof2k2_c3.rom,1000000,800000,959FAD0B,0
kof2k2_c4.rom,1000001,800000,EFE6A468,0
kof2k2_c5.rom,2000000,800000,74BBA7C6,0
kof2k2_c6.rom,2000001,800000,E20D2216,0
kof2k2_c7.rom,3000000,800000,8A5B561C,0
kof2k2_c8.rom,3000001,800000,BEF667A3,0
与程序段同样重要的一部分。一种情况是像上面那样第一个文件基地址为0,第二个文件基地址为第一个文件的基地址加1,第三个文件的基地址是前面两个文件的大小之和加上第一个文件的基地址(800000 + 800000 + 0 = 1000000,注意是16进制的,别当成10进制来算),第四个文件的基地址为第三个文件的基地址加1(1000000 + 1 = 1000001),第五个文件的基地址是前面两个文件的大小之和加上第三个文件的基地址(800000 + 800000 + 1000000 = 2000000),第六个文件的基地址为第五个文件的基地址加1(2000000 + 1 = 2000001),依此类推。还有一种情况是图形文件的第一个文件的大小为400000(4M)那第一个文件的基地址变为400000,后面文件基地址的算法第一种情况相同。
也许你已经发现了图形段堤基地址算法就是:设n为当前的文件编号,若n = 1且 n的大小不等于400000那基地址为0,若n = 1且 n的大小等于400000那基地址变为400000。若n为奇数且不等于1那第n个文件的基地址等于第n – 2个文件与n – 1个文件大小之和加上第n – 2文件的基地址,若n为偶数那第n个文件的基地址便是n – 1个文件的基地址加1。
下面以Capcom CPS2游戏Street Fighter Alpha 3 (US 980904)的RomData为例分析Capcom CPS2游戏RomData的写法。除基地址的算法之外其余的都与SNK MVS游戏的写法相同所以我就不再啰嗦了。
程序段的写法
[Program]
sz3u.03c,0,80000,E007DA2E,0
sz3u.04c,80000,80000,5F78F0E7,0
sz3.05c,100000,80000,57FD0A40,0
sz3.06c,180000,80000,F6305F8B,0
sz3.07c,200000,80000,6EAB0F6F,0
sz3.08c,280000,80000,910C4A3B,0
sz3.09c,300000,80000,B29E5199,0
sz3.10b,380000,80000,DEB2FF52,0
很明显程序段的基地址就是第一个文件的基地址为0,当前文件的基地址为上一个文件的基地址加当前文件的大小。
解密段的写法
[Decryption]
sz3ux.03c,0,80000,7091276B,0
sz3ux.04c,80000,80000,83B213B1,0
解密段的基地址与程序段的算法相同。
图形段的写法
[Graphics]
sz3.13,0,400000,F7A60D9,0
sz3.15,2,400000,8E933741,0
sz3.17,4,400000,D6E98147,0
sz3.19,6,400000,F31A728A,0
sz3.14,1000000,400000,5FF98297,0
sz3.16,1000002,400000,52B5BDEE,0
sz3.18,1000004,400000,40631ED5,0
sz3.20,1000006,400000,763409B4,0
图形段的基地址的算法就比较麻烦。看文件的个数,如果图形文件大于4个,先看前4个扩展名为奇数的文件,这四个文件的在这里分别是sz3.13、sz3.15、sz3.17、sz3.19,它们的基地址是第一个文件的基地址为0,后面的依次累加加2就行了,基地址是0、2、4、6。再看前4个扩展名为偶数的文件,这四个文件的在这里分别是sz3.14、sz3.16、sz3.18、sz3.20,它们的基地址为前四个扩展名为奇数的文件大小之和再依次累加2,基地址是1000000、1000002、1000004、1000006。如果还有文件那就还是先看扩展名为奇数的,
不过基地址就是前面所有的文件的大小之和再依次累加2,例如还有四个文件sz3.21、sz3.23、sz3.25、sz3.27那它们的基地址分别是是2000000、2000002、2000004、2000006。
若图形文件只有4个,而且扩展名都为奇数且文件扩展名小于等于20,例如btc.13、btc.15、btc.17、btc.17,那它们的基地址依次是0、2、4、6。
若图形文件只有4个,而且扩展名都为奇数且文件扩展名大于20,例如sfx.21、sfx.23、sfx.25、sfx.27,那它们的基地址依次是C00000、C00002、C00004、C00006。
若图形文件只有4个,而且扩展名都为偶数,例如sfz.14、sfz.16、sfz.18、sfz.20,那它们的基地址依次是800000、800002、800004、800006。
Z80段的写法
[Z80]
sz3.01,0,20000,DE810084,0
sz3.02,28000,20000,72445DC4,0
Z80文件最多只有两个,第一个文件的基地址为0,第二个文件的基地址为28000。
采样段的写法
[Samples]
sz3.11,0,400000,1C89EED1,0
sz3.12,400000,400000,F392B13A,0
解密段的基地址与程序段的算法相同。
有的游戏还有Parent,即父Rom,一般都是为解密的Rom。像Kof99nd它的Parent是Kof99,只需在Game后面加上Parent: Kof99就行了。
系统段的写法
[System] //SNK MVS
CartridgeID: 267
GfxCrypt: 0
GfxKey: 0
ButLayout: 9
Fix: 0 [System] //Capcom CPS2



ButLayout: 0
Fix: 0

CartridgeID(游戏发行号)这个值是保存在SNK MVS 游戏P1 Rom中的,可以随便写。Nebula便是通过对这个值的比较来决定这个游戏是否应该模拟。修改这个值(当然是修改P1 Rom,修改RomData中的CartridgeID是没用的)可以让Nebula模拟本不该模拟的游戏。Capcom CPS2没有这个项目。
GfxCrypt(游戏用的解密XOR表),这个表被用来解密Rom的图像文件。SNK游戏也有解密表,只是不像CPS2游戏那么变态罢了。SNK的加密表都是固定的,只分为Kof99表和Kof2000表两种。早期MVS游戏是没有加密这一说的,而从Kof99开始为防盗版一如这一技术,而又因为Kof99的解密表被破解,所以Kof2000又采用了新的解密表,不过很快又被破解了,不知道SNK下一步会采用什么技术,也许只有开发新机板了。Capcom CPS2的解密XOR表每个游戏都有不同的解密XOR表,所以没有这个项目。(其实CPS 2游戏的XOR表也有规律只不过这个规律只有CPS2Shock掌握罢了)
GfxKey(XOR表的初始值)SNK MVS解密游戏都为0,其它加密游戏的值视加密方法而定,KOF99加密方式为1,KOF2K加密方式为2,KOF2K1加密方式为1E, KOF2K2加密方式为EC,MS4加密方式为31,龙吼加密方式为3F等。Capcom CPS2连固定的解密表都没有,这个项目肯定就不会有了。
ButLayout(输出方式)SNK MVS游戏为9也只能为9。Capcom CPS2游戏就比较麻烦,大部分游戏为0就OK了,也有为1或2的。
Fix(修正方式)据体算法不明,也是写0就OK。
这这篇文章到目前为止还有很多地方不明,还请大家帮忙补全。也会有一些错误,亦请大家指正。我已经根据这篇文章写了一个专门生成RomData的软件-RomData Maker,如果大家觉得手写太累就用这个软件吧。最后谢谢大家支持。