代码改变世界

[翻译] WindowsPhone-GameBoy模拟器开发二--Rom文件分析

2013-05-21 19:59  Hundre  阅读(2073)  评论(0编辑  收藏  举报

距离上一篇文章的发布已经快一年了,在第一篇文章发布之后才发现原来一个模拟器真的不是一般的大,也可能和我的学艺不精有关,这期间花了大量的时间来学习,终于又决定继续写下去,不过还是一些基础的东西,希望被标题吸引过来的朋友不要太失望

卡带头部:
在卡带中,内部信息位于0100-014F的这个地址区间中。它包含以下内容

0100-0103-入口点
在显示完任天堂的LOGO后,内置的启动程序会跳到这个地址(100h),然后在从这里跳转到位于卡带内的实际程序。通常情况下,这个4字节的区域包含有一条JP 0150h指令,后面跟着一条NOP指令。但也并不总是如此

0104—0133—任天堂LOGO
这些字节定义了任天堂LOGO的位图图像,这个图像会在gameboy启动是显示。这个位图的16进制数据为:
CE ED 66 66 CC 0D 00 0B 03 73 00 83 00 0C 00 0D
  00 08 11 1F 88 89 00 0E DC CC 6E E6 DD DD D9 99
  BB BB 67 63 6E 0E EC CC DD DC 99 9F BB B9 33 3E
Gameboy的启动程序会在现在它们之后校验这些数据,如果数据不对,就自己把自己锁住。CGB只校验前面18个字节,其他的如果pocket gameboy校验全部的30h个字节。

0134—0143—标题
游戏标题,用ASCII码表示的大小字母。如果标题字数少于16个字母,余下的部分用00h填充。在开发CGB是,任天堂把这一区域缩小到15个字母,几个月之后,他们有把它缩小到只有11个字母。新的标题结构的其他字节表示的意思如下:
013F—0142—制造商代码
在老的卡带里面,这一区域是标题的一部分(如上所诉),在新的卡带中,这一区域包含一个用4个大写字母表示的制造商代码。代码的详细意思未知。
0143-CGB标志
在老的卡带里面,这一区域是标题的一部分(如上所诉)。在CGB卡带中,这一标志的高位用来设置CGB功能。这是必须的,否则,CGB把自己转换为非CGB模式。这一标志的典型值有:
80H—支持CGB功能的游戏,但也能在老的gameboy下工作。
C0H-只能在CGB下工作(physically the same as 80h)
如果第7位被置位,或者2、3位中的某一位被置位,gameboy会被切换到一个特殊的没有初始化调色板的非CGB模式下。还不知道为什么要这么做,后来这一模式被用来支持在ROM的特定位置有固定调色板数据的单一色彩的游戏。

0144—0145—新的许可证代码
指定一个2个ASCII字母的许可证代码,用来表示游戏的发行商或者开发公司。这两个字节只在最新的游戏中被使用(“最新”指的是在SGB发布之后上市的游戏)。老游戏只用在014B位置的的头部条目

0146-SGB标志
指定游戏是否支持SGB功能,常见的值有:
00H=没有SGB功能(通常情况下只有普通gameboy或者CGB是这样)
03H=支持SGB功能的游戏
SGB会自己把SGB的功能禁止掉,如果该值不是03H的话

0147—卡带类型
指定在卡带中使用了哪种内存控制器(如果有的话),也用来指定卡带是否使用了其他的硬件。
00h  ROM ONLY                 13h  MBC3+RAM+BATTERY
  01h  MBC1                     15h  MBC4
  02h  MBC1+RAM                 16h  MBC4+RAM
  03h  MBC1+RAM+BATTERY         17h  MBC4+RAM+BATTERY
  05h  MBC2                     19h  MBC5
  06h  MBC2+BATTERY             1Ah  MBC5+RAM
  08h  ROM+RAM                  1Bh  MBC5+RAM+BATTERY
  09h  ROM+RAM+BATTERY          1Ch  MBC5+RUMBLE
  0Bh  MMM01                    1Dh  MBC5+RUMBLE+RAM
  0Ch  MMM01+RAM                1Eh  MBC5+RUMBLE+RAM+BATTERY
  0Dh  MMM01+RAM+BATTERY        FCh  POCKET CAMERA
  0Fh  MBC3+TIMER+BATTERY       FDh  BANDAI TAMA5
  10h  MBC3+TIMER+RAM+BATTERY   FEh  HuC3
  11h  MBC3                     FFh  HuC1+RAM+BATTERY
  12h  MBC3+RAM

注:BATTERY为电池,RAM为随机存储器

0148—卡带的ROM容量
指定卡带的ROM的大小,典型的计算方式为"32KB shl N".
00h -  32KByte (no ROM banking)
  01h -  64KByte (4 banks)
  02h - 128KByte (8 banks)
  03h - 256KByte (16 banks)
  04h - 512KByte (32 banks)
  05h -   1MByte (64 banks)  - only 63 banks used by MBC1
  06h -   2MByte (128 banks) - only 125 banks used by MBC1
  07h -   4MByte (256 banks)
  52h - 1.1MByte (72 banks)
  53h - 1.2MByte (80 banks)
  54h - 1.5MByte (96 banks)
注:bank指的是内存块,不是银行哦

0149—RAM的大小
指定卡带中额外的RAM的大小
00h - None
  01h - 2 KBytes
  02h - 8 Kbytes
  03h - 32 KBytes (4 banks of 8KBytes each)—8K字节占用一个内存快
如果使用MBC2类型的卡带,这个字节必须被设置为00H。尽管MBC2有自带的512*4 个位大小的RAM

014A—目标代码
指定这个版本的游戏是否能在日本销售,或者只能在其他地方销售。只定义了两个值:
00h - Japanese
  01h - Non-Japanese

014B—旧许可证代码
指定游戏/发行商的代码,范围为00-FFh。值33h用来指明在0144-0145存在新的许可证代码。
在SGB中,如果值不是33h,则SGB无法工作

014C-游戏版本掩码(mask)
指定游戏的版本号,通常为00h

014D-头部校验和
包含一个跨越0134-014C的大小为8位的校验和。校验和的计算方式如下:
x=0:FOR i=0134h TO 014Ch:x=x-MEM-1:NEXT
这个计算结果的底8位必须和该位置的值相等。如果校验和错误,游戏则不会运行。

014E—014F-全局校验和
包含一个跨越整个卡带ROM的大小为16位的校验值。计算方式为:
除了这两位外,把卡带的所有位相加得到的值。如果校验和错误,游戏则不会运行

翻译的原文地址为:http://nocash.emubase.de/pandocs.htm