作者erspicu (.)
看板Emulator
标题[心得] NES的开发timing杂谈
时间Tue Mar 10 01:04:04 2026
比较偏给对软硬体模拟开发等议题有关的人分享
"
https://github.com/100thCoin/TriCNES 这专案评价如何?"
TriCNES 是个很有意思但也颇具争议的专案。让我从几个面向整理一下:
专案本质
TriCNES 是由 Chris "100th_Coin" Siebert 用 C# 写的 NES 模拟器,全名叫做「
Coin's Contrabulous Cartswapulator」,专注於测试驱动的精确度。它最初是为了实验
一个叫做「Intercycle Cartridge Swapping」的理论 — 在每个 CPU cycle 之间更换卡
带来执行自订程式码。这个概念本身非常疯狂且富有创意。
精确度成绩亮眼,但有脉络
作者同时开发了 AccuracyCoin 测试 ROM,而 TriCNES 在自己的测试中拿到满分。不过
这正是争议所在。
社群的主要质疑
有人提出应该谨慎看待这些结果,指出 TriCNES 虽然号称追求「speedrun 精确度」,但
它甚至无法正确输出音讯。 此外,也有人批评说「我的模拟器在我自己开发的测试
ROM 上最精确」这件事本身就不是一个经过充分审计的精确度主张。
从功能面来看限制也很明显:它只能正确执行 NTSC 卡带,而且只支援少数几个 mapper
(0、1、2、3、4、7、9、69)。更有人指出,TriCNES 目前甚至不接受手把输入
,只能用 TAS 档案回放,所以作为一般使用者来说根本无法「玩」游戏。
测试 ROM 本身的争议
AccuracyCoin 的测试是针对特定的 NES 硬体版本(RP2A03G CPU 和 RP2C02G PPU)设计
的,在不同版本的实机上也可能会失败,目前看来只有一种 NES 版本能跑出满分。
但也有不可否认的贡献
作者花了 8 个月专注在模拟器精确度上,并坦承说它不完美,但认为跟 Bizhawk 相当
— 有些测试 TriCNES 过但 Bizhawk 没过,反之亦然。 而且 AccuracyCoin
测试 ROM 确实推动了整个 NES 模拟生态的进步,MiSTer 的开发者 Kitrinx 就是用它来
改进 NES core 的精确度。
总结来说,TriCNES 与其说是一个「最精确的 NES 模拟器」,不如说是一个极度特化的
研究工具 — 它在 CPU cycle 层级的时序行为上下了很深的功夫,但牺牲了音讯、
mapper 广度、和一般游玩功能。它的价值更多在於它推动了精确度测试的标准化,以及
「intercycle cart swapping」这个疯狂概念的验证。
"所以针对任天堂不同型号的cpu ppu,实际硬体行为也不同相同?"
没错,这是一个非常实际的问题,而且答案是肯定的 — 不同版本的 CPU 和 PPU 在硬体
行为上确实存在差异。
CPU(2A03)方面,已知的版本包括无字母版(最早期)、E、F、G、H 等。最早期的无字
母版 RP2A03(用在所有 VS. System 大型电玩基板上)完全没有实作「短周期噪音」(
short period noise)模式,设定对应的 bit 完全没有效果。这就是一个具体的功能差异。
另一个有趣的差异是 Pin 30 的行为:在 RP2A03G 上拉高这个脚位会启用额外的音讯硬
体诊断暂存器($4018-$401A),但在 RP2A07(PAL 版)和 RP2A03E 上,拉高同一个脚
位反而会透过停用内部 6502 的 /RDY 输入来让 CPU 停止执行。同样的引脚,不同版本做完全不同的事。
PPU(2C02)方面差异更多。不同版本在开机时萤幕颜色就不一样 — 2A03E/2C02E 组合
通常显示紫色或棕色,而较新的版本则总是灰色。此外还有 RP2C03、RP2C04、
RP2C05 等变体,这些主要用在大型电玩基板如 PlayChoice-10 和 VS. System 上,它们
输出原生 RGB 而非 composite,而且色盘也不同,有些游戏看起来会有明显差异。
PAL 版本的差异更是根本性的。PAL 版的 RP2A07 和 NTSC 版相比,输入时脉分频器
不同(除以 16 而非除以 12)、各种计时器查表值(噪音、DPCM、frame timer)都不同
。 PAL 版的 RP2C07 和 NTSC 版 PPU 相比,差异包括时脉分频器、每帧扫描线数
量及相关时序细节、产生的视讯讯号、sprite RAM 刷新逻辑,以及改进的 I/O 暂存器同
步。
还有一个值得一提的层面:CPU 开机和重置时的初始状态(暂存器和 RAM 内容)也不能
被视为确定的。 NESdev不同主机可能开机後 RAM 的内容就不一样,很多商业和自制游戏
的 bug 就是因为错误地依赖了初始系统状态。
这就是为什麽前面提到 AccuracyCoin 测试 ROM 会注明它是针对 RP2A03G + RP2C02G 设
计的 — 因为「精确」这件事的前提是:你到底要精确模拟「哪一台」NES?不同版本的
实机本身行为就不完全一致,所以模拟器和 FPGA 核心必须选定一个特定版本作为目标。
大多数模拟器和 MiSTer 都以最常见的 G 版为基准。
"也就是说真实游戏主机跑ac test,可能会因为cpu ppu的型号差异,导致分数比122更低?"
对,这是完全确定的事实,而且不只是「可能」,是「必然」。
从前面的资料就能拼出完整的图像。AccuracyCoin 明确说明它是针对 RP2A03G CPU 和
RP2C02G PPU 设计的,不同版本的硬体上某些测试可能会失败。 GitHub而实际测试显示
目前只有一种 NES 版本能在这个测试中拿到满分。具体来看几个已知的例子:
一台真实的 AV Famicom 只拿到 121/125,而且它失败的项目跟 MiSTer 失败的不一样
。 MiSTer FPGA这就代表真实硬体本身就不是「标准答案」。
再想想前面谈过的版本差异。早期无字母版的 RP2A03 连 short period noise 都没实作
,这种主机跑 APU 相关的测试一定会挂。RP2C02E-0 及更早的版本 OAMDATA 和调色盘
RAM 不可读,如果测试项目涉及这些读取行为也会失败。PAL 的 RP2A07/RP2C07 就更不
用说了,时脉分频、扫描线数量、frame timer 全部不同,拿去跑 AccuracyCoin 大概会
惨不忍睹。
所以实际情况是这样的阶层关系:
特定的 RP2A03G + RP2C02G 组合 → 接近满分(但即使同型号,个体差异也可能导致少
数测试结果不同)
AV Famicom(通常搭载较晚期的 H 版)→ 121 左右
早期 Famicom(E 版或更早)→ 预期会更低
最早期无字母版(VS. System 大型电玩用)→ 可能明显更低
PAL 主机 → 根本不适用这个测试
山寨机 → 结果不可预测
有人甚至指出了一个有趣的矛盾:通过所有测试意味着你完美模拟了 revision G 的行为
,但这反而代表你「无法」正确执行某些依赖其他版本行为的 Famicom 游戏。 MiSTer
FPGA
所以你的 122 分不只是比某些真实主机更高,从某个角度来说,它可能比大多数现存的
真实 NES/Famicom 主机都更「标准」— 因为你的模拟器是以理想化的 G 版规格为目标
,而真实硬体则受限於它出厂时装了哪个版本的晶片。
"目前最新测试ac test是136分.实际上我拿136分也不一定代表100%准确,只是代表符合了
某种特定机型的特性?"
没错,你的理解完全正确。
136/136 满分只代表一件事:你的模拟器在这 136 个测试项目上的行为,与作者手上那
台特定的 RP2A03G + RP2C02G 主机一致。它不等於「100% 精确」,原因有好几层:
第一,测试覆盖率永远是有限的。NESdev Wiki 上对此有很精辟的区分 — 「相容性
」是指模拟器对已知程式产生相同输出,而「精确度」是指对任意未知程式也能产生相同
输出。精确度无法被直接测量,要在数学上证明模拟器等价於真实硬体,本质上是不可判
定问题。 NESdev136 个测试只是从无限可能的硬体行为中挑出的 136 个切面,NES 内部
还有大量未被测试到的交互行为。
第二,同型号晶片之间也有个体差异。半导体制程本身就存在微小的变异,同样标记
为 RP2C02G-0 的两颗 PPU,在极端边界条件下的行为可能不完全一致。开机时 RAM 的初
始值就是最明显的例子 — 有些主机开机後 RAM 内容可能是一致的,但其他主机可能不
是, NESdev这种差异在晶片层级是不可控的。
第三,测试本身可能有盲区或偏见。AccuracyCoin 的作者同时也是 TriCNES 的作者
,有人质疑这构成了「用自己的测试验证自己的模拟器」的循环论证。 测试项目的选择必然反映了作者对「什麽行为重要」的判断,而不是硬体行为的完整描述。还有
其他测试 ROM 套件(如 blargg 的各种测试、Mesen 的测试等)可能会测出
AccuracyCoin 没覆盖到的问题。
第四,「准确」到哪个层级?目前的测试大多关注 cycle 层级的行为,但真实硬体
还有 sub-cycle 的类比特性 — 电压的上升/下降时间、汇流排上的电容效应、晶片之间
的信号传播延迟等。Visual 2A03/2C02 专案已经做到了电晶体层级的模拟,但即使如此也不可能完美复制物理晶片的每一个电气特性。
所以比较健康的看法是:AccuracyCoin 是一把很好的尺,但它量的是「与 G 版硬体在这
些特定行为上的吻合度」,而不是「绝对精确度」。136/136 代表你的模拟器在目前已知
的、被认为重要的行为上表现优秀,但没有任何有限的测试能证明「100% 精确」— 这在
逻辑上就做不到。
ps.目前冲到132/136,但其实是没啥意义的,不过就虚无的爽感而已
实际上看完这AI说法一度想暂停,但反正是ai烧TOKEN不是烧我的脑....
所以最後我用AccuracyCoin自己开发的模拟器(似乎完美通过自己的测验XD)来参考,
它的code真的是非常非常的硬体底层低阶描述,所以code的量很大,
说是参考,更直接是说看它的sources是怎样描述硬体规格和行为,
实际上比较厉害的不是做软体的,反来是有办法逆向挖出硬体特性的人,
我只是拿做好功课的答案去想办法把正确结果凑出来而已.
(可能是争议偏高,AccuracyCoin作者自己本人写的模拟器反来非常低调,
搞到根本不太能用...)
感觉应该是可以冲到136满分,接下来会慢慢转移到周边功能.效能之类的,
再後续是希望用一些教学分享.还有把核心弄更友善,以後不管有人没有人用aprnes,
哪天有人有兴趣可以用核心组件套自己的介面去用,简单来说library化.
AprNes一直都偏向於技术研究.验证.教育用途性质的专案,
兴趣使然下班无聊玩的东西
--
※ 发信站: 批踢踢实业坊(ptt.cc), 来自: 182.233.248.16 (台湾)
※ 文章网址: https://webptt.com/cn.aspx?n=bbs/Emulator/M.1773075863.A.257.html
※ 编辑: erspicu (182.233.248.16 台湾), 03/10/2026 01:08:02
※ 编辑: erspicu (182.233.248.16 台湾), 03/10/2026 01:11:09
1F:推 sdbsy14242: 满有趣的,感谢分享 03/10 09:00
2F:→ RuinAngel: 追求满分没意义但可以从测试里知道哪些项目没准有修正 03/10 09:44
3F:→ RuinAngel: 空间还是很棒啊,至於作者的模拟器根本只是概念实作化 03/10 09:44
4F:→ RuinAngel: 的样品其实也无损这个测试的实际用途 03/10 09:44
5F:推 zack867: 我觉得对一般玩家来说差最大的其实是palette色彩跟电视sh 03/10 12:58
6F:→ zack867: ader啦 03/10 12:58