As per Nick Westgate's comment (hence the instant community wiki), the loading procedure is a bit more complicated than you might naively guess:
For now, you can load 0x4000 bytes starting at offset 0x0010, and map
that as ROM into both $8000-$BFFF and $C000-$FFFF of the emulated
6502's memory map.
The 'for now' assumes you're going to write a NES emulator and therefore one day will properly parse the NES-related file format that test is stored in and emulate the NES-specific memory mapping scheme that leads to the mirroring of contents.
Ignore the comment in the post before that you should "[log] your PC (and registers) on every cycle", and the implication of the same in that post and onwards; he means that:
- before fetching the first operation code byte, make an internal record of the program counter and other registers;
- after reading the final operand byte, log all the values you stored back in step (1) plus the full instruction and its disassembly.
If you've simplified things in your emulator to read and execute each operation atomically and then skip time ahead by the number of cycles you should have spent working then you can probably omit the temporary storage. I suspect the author that generated the sample log had implemented such an emulation. Key clues will be a switch
table indexed by opcode that is not in some way a coroutine, and/or a lookup table of instruction lengths.
Further advice:
The NES doesn't actually use a 6502. It uses a clone that omits decimal mode — the decimal flag simply has no effect. So if you're emulating a 6502, expect test results to vary there.
For other good 6502 tests, see:
- AllSuiteA (tests a whole bunch of things and gives you a pass or fail);
- Klaus Dormann's tests (slightly more of a hassle; will simply enter an infinite loop somewhere if a particular test fails. You'll need to inspect the source to find out which failure you've got); and
- Wolfgang Lorenz's tests (a whole bunch of separate tests, originally for running separately on a C64 but easy enough to run without anything implemented beyond a 6502 other than that it'll provide text output of status in PETSCII, so you'll also need a quick lookup table to map that to ASCII).
I used all three of those to bootstrap my most recent 6502 emulator, plus some self-written cycle-by-cycle tests for things like interrupts that you wouldn't expect code that sits inside a 6502's address space to be able to handle.
I found out a lot later that I had a very minor deviation in decimal handling — minor enough to pass all those tests, but not sufficient to pass an exhaustive 6502 comparison. I conveniently found a better test in the Acorn BBC community, within the archive attached to this post. I elected to run that by:
- load the contents of
BCDTEST_beeb
at 0x2900
;
- write
JSR 2900h
to address 0x200
;
- put an
RTS
at 0xffee
, but also make sure you can trap that address;
- set the program counter to
0x200
and keep running until it is at 0x203
;
- then test that the value at
0x84
is 0
. If it is something else, that indicates failure.
To get more feedback, any time the PC goes to 0xffee
, output the ASCII character in the A register.