cpu cycle timing with nestest.nes, branch instructions

This is an archive of a topic from NESdev BBS, taken in mid-October 2019 before a server upgrade.
View original topic
cpu cycle timing with nestest.nes, branch instructions
by on (#12166)
i noticed that a few links to nestest.nes and nestest.txt are not working; the wiki for example. i have a copy and dont need it, but someone else i was chatting with did need it.

i read several different manuals that the branch instruction can be 2, 3, 4, or 5 cycles long depending if it branches and if there are 1 or more page crosses. does anyone have any info that would explain this more?

awhile back quietust and blargg posted a dump of nestest.nes and i think quietusts' had the cycle timing on his. that link is missing. i requested before and will again, i think the nestest.log should be added to the wiki. i think the log should contain the cpu information, memory reads/writes and cycle timing. is there anyway of writing a test for the nes or logging it from a original nes?

i would test and post this info myself if i knew i was 100% accurate and had the hardware to do so.

thanks to all that have made these test roms !!

matt

by on (#12167)
maybe another test for cycles and page crossing, the invalid reads before a re-read

by on (#12171)
http://www.tripoint.org/kevtris/mappers/incoming/

Both ROM and txt.

Here is the lowdown on branching;

Code:
inline void OperationCode?0()
{
   if( ... )
   {
      if( (unsigned char)CPU.PC + Relative > 0xFF || (unsigned char)CPU.PC + Relative < 0 )
         CPU.CC++;
      CPU.PC += Relative;
      CPU.CC += 3;
   }
      else
   {
      CPU.PC += 2;
      CPU.CC += 2;
   }
}


So if there is no branch then add 2 CC's. If there is a branch then add 3 CC's. If the branch is to another page then add 1 CC.

by on (#12178)
For my best, this is the correct drill...

1 cycle to fetch the instruction byte
1 cycle to fetch the argument byte (signed char)
if true:
+ 1 cycle to fetch the next instruction byte (and throw it away)
+ 1 extra cycle if page is crossed

No clue about a 5th or even a 6th cycle being executed though.
Re: cpu cycle timing with nestest.nes, branch instructions
by on (#12181)
mattmatteh wrote:
i read several different manuals that the branch instruction can be 2, 3, 4, or 5 cycles long depending if it branches and if there are 1 or more page crosses. does anyone have any info that would explain this more?


6502_cpu.txt explains it very well. But note its line about the last cycle not counting as part of the instruction (therefore while it shows a 5th cycle, the most there ever are in a branch is 4). In its example... the last byte fetched is used as the opcode for the next instruction to be exeucted (so that cycle actually counts as the first in the next instruction -- not as part of the branch).



I wish I knew a way for a test ROM to check cycle timing.... but how could you test something like that?

by on (#12182)
thanks for the replies.

disch, when i was reading that i was kinda thinking that might be the case. seems confusing like that.

matt
Re: cpu cycle timing with nestest.nes, branch instructions
by on (#12183)
Disch wrote:
I wish I knew a way for a test ROM to check cycle timing.... but how could you test something like that?

Disable IRQ, enable NMI, wait for event of known time (e.g. NMI), execute operation many times, wait for event of known time, calculate time elapsed.

by on (#12185)
hmmm, need a test rom for that. not sure if i could write one. ill try, but not sure when ill get that done. still working on my nes.

matt

by on (#12211)
disch,

thats what i read that showed 5 intructions. seems that is wrong ?

matt

by on (#12214)
no...

the last cycle is the opcode fetch for the NEXT instruction (it's just showed there to show where the CPU is reading its dummy reads from). Like it says in the doc (and in my previous post)... branches are actually 1 cycle shorter than that doc says, because the last cycle isn't really part of the branch.

by on (#12216)
ok, got it. thanks