It is currently Fri Aug 23, 2019 2:09 am

All times are UTC - 7 hours





Post new topic Reply to topic  [ 12 posts ] 
Author Message
 Post subject: Nintendulator log change
PostPosted: Sat Jul 20, 2019 10:05 am 
Offline

Joined: Sat Aug 25, 2018 7:21 am
Posts: 40
Hi,
I was looking for a nestest log, since the one I used to test my 6502 emulator disappeared from my computer. I found it in the wiki. However, when I tested my emulator its output and the log provided in the site didn't match. That seemed strange, since I remember it worked like a charm last year. I've just known that the file was changed (by observing cached versions of the page), and the version hosted back then matches my emulator's output. The new version renames CYC as PPU (that's ok, since it refers to PPU dots). However it now adds an unnamed column and CYC (I suppose it means actual CPU cycles). However, I'm unable to match CYC with CPU cycles. Aren't they supposed to be 1/3 of the PPU cipher? On top of that, should I worry about this, since PPU (previously CYC) matches (I mean, in terms of accuracy)?


Top
 Profile  
 
PostPosted: Sat Jul 20, 2019 2:42 pm 
Offline
User avatar

Joined: Sun Sep 19, 2004 9:28 pm
Posts: 4208
Location: A world gone mad
Lots of misinformation being stated here. Let's clarify, with links/references to literally everything:

1. CPU cycles are independent of PPU dots ("cycles"); the two chips (CPU and PPU) are operating independently of one another. On NTSC, for every 1 CPU cycle, 3 PPU dots happen. Reference

2. CPU cycles are pre-defined and can be looked up in any good/decent 6502 reference chart/manual/books/links. An instruction takes N number of cycles, sometimes with some variance (e.g. branch instructions take an extra cycle if the branch is taken, page wrapping costs an extra cycle, etc.). Good materials will disclose this information. See the Wiki for such, or other online resources. Reference

3. CYC in nestest.log refers to CPU cycles, not PPU. It is an incrementing counter. The nestest entry on the wiki page includes documentation (more on that in a moment).

4. PPU in nestest.log consists of two numbers: the PPU X counter and the Y counter (as in X dot and Y scanline position), delimited with a comma and some space padding. See Quietust's post below for details, else for PPU rendering details: Reference

5. The values shown in A/X/Y/P/SP/PPU/CYC are the values **before** the instruction on that line has executed. The reason the first line has CYC:7 is because internally when the CPU starts, it does a bunch of "prep work". There is some variance between 6502 CPU models (MOS 6502 vs. NES vs. others), where some take 9, others take 8 or 7, but the details are here: Ref 1 Ref 2 Ref 3 Ref 4

6. An FYI useful for emulator authors: nestest.log starts at $C000, not at the actual RESET vector value that's in ROM ($C004). I believe what's actually been done is overriding the vector value to contain $C000 (see #5 above). This runs all the tests, with no interactive menu. This is described in the documentation that comes with the nestest ROM but is easily overlooked. All emulator authors should read -- not skim -- the documentation that comes with nestest.

7. nestest documentation has a section called "Final notes" that is incredibly important to read. It is common for emulator authors to get errors/mistakes in an instruction or addressing mode, only to fix the bug and then get an error in an "earlier/previous" test number, which often causes confusion ("33 was failing before, now I fixed that and 32 is failing!!"). Read that section for why.

8. Emulator authors need to understand that nestest is not going to guarantee that all of your opcodes are functioning flawlessly; it (legitimately) assumes that there is a base set of instructions that are working/implemented properly. This has come up repeatedly on the nesdev Discord, where some emulator authors passed some tests but not others, only to find that previously-passing instructions were actually incorrectly implemented. Your emulator = your code = your bugs = you get to figure out why.

Additionals, because they come up all the time:

* For bugs with power-on and/or RESET states of the CPU, or register values/flags/etc., refer to the wiki. Reference

* For issues with the B flag of P (you will encounter this with regards to PHP/PLP/RTI), refer to the wiki or this explanation (see 41:58 onward).

Edit: bunch of additions and fixes.


Last edited by koitsu on Sat Jul 20, 2019 5:41 pm, edited 1 time in total.

Top
 Profile  
 
PostPosted: Sat Jul 20, 2019 4:46 pm 
Offline
User avatar

Joined: Sun Sep 19, 2004 10:59 pm
Posts: 1473
koitsu wrote:
4. PPU in nestest.log is an incrementing counter of PPU dots ("cycles').

Minor correction: there are two values, one for the PPU's X counter and one for its Y counter. Observe that the log's first line has "PPU: 0, 0" while the last one has "PPU:188,233" and that the second number never overflowed (which is good, because I don't count the number of frames rendered) - this means it took 233 full scanlines and 188 additional dots to execute.

_________________
Quietust, QMT Productions
P.S. If you don't get this note, let me know and I'll write you another.


Top
 Profile  
 
PostPosted: Sat Jul 20, 2019 5:35 pm 
Offline
User avatar

Joined: Sun Sep 19, 2004 9:28 pm
Posts: 4208
Location: A world gone mad
Quietust wrote:
koitsu wrote:
4. PPU in nestest.log is an incrementing counter of PPU dots ("cycles').

Minor correction: there are two values, one for the PPU's X counter and one for its Y counter. Observe that the log's first line has "PPU: 0, 0" while the last one has "PPU:188,233" and that the second number never overflowed (which is good, because I don't count the number of frames rendered) - this means it took 233 full scanlines and 188 additional dots to execute.

Thank you! 100% right, and very easily overlooked due to space-padding after the comma. I've edited my post to clarify.


Top
 Profile  
 
PostPosted: Sun Jul 21, 2019 8:01 am 
Offline

Joined: Sat Aug 25, 2018 7:21 am
Posts: 40
Thank you very much for your answers! They were quite clarifying.


Top
 Profile  
 
PostPosted: Sat Aug 03, 2019 10:41 am 
Offline

Joined: Sat Aug 25, 2018 7:21 am
Posts: 40
I'm trying to replicate Nintendulator's log (I overlooked some details in the past and this lack of information is making progress difficult). I'm having some trouble with this instruction from nestest (line 5013 of http://www.qmtpro.com/~nes/misc/nestest.log):

Code:
C6C9  0C A9 A9 *NOP $A9A9 = A9                  A:55 X:00 Y:53 P:24 SP:F7 PPU:164,131 CYC:14952


Why is it showing A9 as the content of address A9A9? This address isn't accessed at any time during the test execution. My output shows 00 instead, which I find logical, unless I'm missing something.

Edit: since $A9A9 lies into cartridge memory space I guess I the cartridge is not properly mapped. Please, tell me if I'm wrong.


Top
 Profile  
 
PostPosted: Sat Aug 03, 2019 6:57 pm 
Offline
User avatar

Joined: Sun Sep 19, 2004 9:28 pm
Posts: 4208
Location: A world gone mad
1. The instruction $0C you see labelled as NOP $A9A9 is an invalid opcode, in case that's confusing you at all. It is not quite a "normal" NOP.

2. nestest.nes is mapper 0, 16KB PRG + 8KB CHR, and is thus mapped to $8000-BFFF in addressing space (i.e. 16KB). NES ROM addressing space runs from $8000-FFFF (i.e. 32KB). In the case of 16KB mapper 0 games, $C000-FFFF is a mirror of $8000-BFFF due to how the board circuitry works. The byte at location $E9A9 (value $A9) is thus the same byte as at $A9A9. https://wiki.nesdev.com/w/index.php/NROM outlines this fact (see "Banks" and read closely; NROM-128 = 16KB PRG, NROM-256 = 32KB PRG).


Top
 Profile  
 
PostPosted: Sun Aug 04, 2019 3:01 am 
Offline

Joined: Sat Aug 25, 2018 7:21 am
Posts: 40
koitsu wrote:
1. The instruction $0C you see labelled as NOP $A9A9 is an invalid opcode, in case that's confusing you at all. It is not quite a "normal" NOP.

2. nestest.nes is mapper 0, 16KB PRG + 8KB CHR, and is thus mapped to $8000-BFFF in addressing space (i.e. 16KB). NES ROM addressing space runs from $8000-FFFF (i.e. 32KB). In the case of 16KB mapper 0 games, $C000-FFFF is a mirror of $8000-BFFF due to how the board circuitry works. The byte at location $E9A9 (value $A9) is thus the same byte as at $A9A9. https://wiki.nesdev.com/w/index.php/NROM outlines this fact (see "Banks" and read closely; NROM-128 = 16KB PRG, NROM-256 = 32KB PRG).


That was it. I read that section, but I didn't get when mirroring should be applied. I was just mapping PRG-ROM to $C000-FFFF.
Thank you.


Top
 Profile  
 
PostPosted: Sun Aug 04, 2019 4:10 am 
Offline

Joined: Sat Aug 25, 2018 7:21 am
Posts: 40
I have another question. Why is $FF value shown as in memory value after performing STA when A contains $02? I'm referring to line 8981 of http://www.qmtpro.com/~nes/misc/nestest.log

Code:
C68B  8D 15 40  STA $4015 = FF                  A:02 X:FF Y:15 P:25 SP:FB PPU: 86,233 CYC:26520


In this case the accumulator is written to an APU register, but by watching the Donkey Kong log from Nintendulator I observed this also happens with PPU registers. Why is that? Does it have to do with _io_db being filled due to the capacitance issue exposed in the wiki https://wiki.nesdev.com/w/index.php/PPU_registers (this whouldn't explain what's going on with the APU registers...)?


Top
 Profile  
 
PostPosted: Sun Aug 04, 2019 5:34 am 
Offline

Joined: Sun Sep 19, 2004 11:12 pm
Posts: 21560
Location: NE Indiana, USA (NTSC)
I haven't looked into it in too much detail. But my guess is that STA shows the old value before the store, and it doesn't show the value of MMIO registers ($2000-$401F) because reading those has side effects.

_________________
Pin Eight | Twitter | GitHub | Patreon


Top
 Profile  
 
PostPosted: Sun Aug 04, 2019 6:03 am 
Offline
User avatar

Joined: Sun Sep 19, 2004 10:59 pm
Posts: 1473
tepples wrote:
I haven't looked into it in too much detail. But my guess is that STA shows the old value before the store, and it doesn't show the value of MMIO registers ($2000-$401F) because reading those has side effects.

That's exactly what it's doing - Nintendulator's debugger assumes the value $FF whenever it is told to "preview" the value at any memory address for which a special "Debug" (side-effect-free) read handler has not been assigned.

_________________
Quietust, QMT Productions
P.S. If you don't get this note, let me know and I'll write you another.


Top
 Profile  
 
PostPosted: Sun Aug 04, 2019 8:01 am 
Offline

Joined: Sat Aug 25, 2018 7:21 am
Posts: 40
Okay, got it. Thank you both.


Top
 Profile  
 
Display posts from previous:  Sort by  
Post new topic Reply to topic  [ 12 posts ] 

All times are UTC - 7 hours


Who is online

Users browsing this forum: No registered users and 3 guests


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Search for:
Jump to:  
Powered by phpBB® Forum Software © phpBB Group