用MAME debugger的Watchpoint监视,可以简单发现:在每一关的开头,以及击杀boss的瞬间,这个地址都会有写入操作;读取则相对非常频繁。结合实际现象,我推测:击杀boss过关的时候,如果屏幕上还有杂兵活着,它们会立刻被一起干掉,然后出结算画面。$FF5FA1就是触发这个判定用的。将它锁成FF的话,游戏就会一直以为你是刚刚过关的状态,因此见谁秒谁,说白了就是这一关内处于秒杀BBOS瞬间的状态,小兵瞬间死亡,不能捡东西灯等,下一关开始重新计算状态(要不得话打死第一关BOSS后就等着通关吧,卡普空想到这一点了),所以无敌只对当前关有效。
那么,摇出来的无敌,跟zakria改出来的无敌,是不是一回事呢?我用「可以摇无敌」的改版ROM(punipic)测试了一下,在第三关摇出无敌(红衣机枪敌人挣脱)的瞬间,执行情况如下:
首先,发挥最关键作用的是$03BF34这句(ROM中是50EDDFA1)。DFA1反汇编显示成-$205F,其实就是$FF5FA1,程序执行到这一句就会给这个地址赋值,也就是触发了无敌状态,然后再往下走到检测时就会触发杀死敌人的效果。换言之,大家熟知的摇无敌确实是$FF5FA1这个地址造成的。zakria改出来的无敌和你摇出来的无敌是一样的。然而正常游戏中并不会出现无敌。在$03BF20这一步,程序会检查D0寄存器的值,如果不等于#$7,就会从$03BF24直接跳到$03BF38,跳过了上述赋值。D0寄存器的值是动态变化的,每一次执行到这里都可能不一样,因此即使在盗版街机上也不是100%能摇出无敌,能摇出来的前提是敌兵挣脱瞬间D0=7。可能是我手法差,总之这里我暂且认为是随机发生的。如果第一步没有拦住(原版也有可能通过第一步),那么往下还会有一个检查,在$03BF28(上图标黄的内容)。它会检查从$000AC6起的四个字节是否等于#$0080014A,如果相等,就跳过去,直接到$03BF38。注意:000AC6是ROM中的内容,值是固定的。继续追查,原版游戏ROM是这样的:
看到0080014A了么?看见了就应该明白,原版游戏中你怎么摇也摇不出无敌的,程序100%会跳过触发无敌的那一句,根本进不去。
能摇出无敌的盗版ROM,则是这样的:
这里被改成了0C409180,因此在BEQ判断处不能正常跳转,于是程序接下来会按顺序执行$03BF34,然后就触发无敌了。
总结一下,在「中国大陆流行的盗版基板」中,触发「无敌bug」的条件是「$03BF20语句执行时D0=#$7,从而未能跳过$03BF34」。而$03BF20会在特定敌兵「TRENCH」(即上图的红衣机枪手)从揪脖子状态挣脱时执行,无论是时间到了自动挣脱,还是玩家摇出了前滚动作中止揪脖子。之所以只有3、5、6关能无敌,是因为这个敌人只在这三关刷新。以上是我可以确定的内容。
1. 在「摇无敌」这个过程中,疯狂左右晃动摇杆可能并没有起到太大作用,只是尽量快速重复「揪脖子,挣脱」这个过程,反复碰运气而已。
2. 「无敌bug」不像是盗版dumpROM时失误所致——盗版ROM和原版ROM不只是一两位数据有出入,光是上面我截图中显示的,从$000AB2到$000B0D都大相径庭,其它还有很多不同之处。我认为这个bug很可能是人为手动修改导致的。『惩罚者』的基板并不是普通的CPS,而是CPS\’(搭载QSound芯片),盗版基板阉掉了QSound,势必要在程序上有些改动。
3. 「无敌bug」也并不像是盗版者故意设计的秘技。就$03BF34这一句以及其附近的代码而言,盗版ROM和原版ROM这里是相同的。我倾向于认为它是盗版者修改程序时意外发生的副作用。至于原版程序为什么要在这个地方留一句进不去的代码,抱歉,我也不知道。只能问当年卡普空的设计者了(或许就怕摇无敌吧)。
4、用作弊码开启无敌以及街机最后一关出无敌,为什么第一关BOSS后不会过关,以及最后一关像第一关BOSS的精英兵不死呢(他俩地址是一样的),一直跟随到通关还跳上车追玩家打。是因为这2个地方的敌兵地址与其它不一样,过关清场是不会死掉,不是小兵的地址不用说了,这2处的兵还与其它关底的BOSS不同。这也就是特殊之处吧。另外第四关也能100%出无敌的,这是借用别人的方法,在这个转载了请多多包涵:
发表评论