65816 JSR (a,x)

This is an archive of a topic from NESdev BBS, taken in mid-October 2019 before a server upgrade.
View original topic
65816 JSR (a,x)
by on (#157890)
My CPU is buggy (maybe very)...

Can't understand how JSR (a,x) or "JSR Absolute Indexed Indirect" works.
It's supposed for making a "Subroutine Table". It's the only opcode that goes out of my scope.
i have read the best docs, but still without understand.

Can somebody explain me?
Re: 65816 JSR (a,x)
by on (#157891)
IIRC

Code:
Proc0: ...

Proc1: ...

Proc2: ...

Table: DW Proc0, Proc1, Proc2

LDX #$02
JSR (Table, X) ; jumps to Proc1


Note that both Table and the Procs need to be part of the current program bank.

That clear things up?
Re: 65816 JSR (a,x)
by on (#157893)
Yes, i understand it from the point of view of writing it in an 65816 asm.
The thing is that i don't know how to implement it in my cpu emu.

Taking into account this:

Code:
   WriteSNesMem(Cpu.SP, LOBYTE(Cpu.PC + 1));
   Cpu.SP--;
   WriteSNesMem(Cpu.SP, HIBYTE(Cpu.PC + 1));
   Cpu.SP--;   
   unsigned char PCL = ReadSNesMem(FULLPC);
   unsigned char PCH = ReadSNesMem(FULLPC + 1);
   //here i should do something with X!!
   MAKEPC(PCL, PCH);


Well the code is self much explicatory.
When do i hell add the X Register?
Re: 65816 JSR (a,x)
by on (#157894)
Add X to the address in the instruction, and the result is the memory location from where the final address will be pulled from.
Re: 65816 JSR (a,x)
by on (#157895)
Add X to FULLPC the provided address before reading memory. Source says it wraps within a 64K bank, and the first byte is written before the return address is pushed.

EDIT: thinko
Re: 65816 JSR (a,x)
by on (#157897)
Thanks tepples... and wow what a good reference page you threw me...
Re: 65816 JSR (a,x)
by on (#157899)
tepples wrote:
Add it to FULLPC

Wait, isn't FULLPC pointing to the instruction itself? As I see it, he has to read the address pointed by FULLPC (i.e. the bytes after the opcode), add X to that, and finally use the result to fetch the new PC value... isn't it?
Re: 65816 JSR (a,x)
by on (#157900)
My bad. Corrected.
Re: 65816 JSR (a,x)
by on (#157928)
EDIT: FULLDBRPC is FULLPBRPC;

So:
Code:
   WriteSNesMem(Cpu.SP, LOBYTE(Cpu.PC + 1));
   Cpu.SP--;
   WriteSNesMem(Cpu.SP, HIBYTE(Cpu.PC + 1));
   Cpu.SP--;   
   Cpu.address = ReadSNesMem(FULLPBRPC);
   Cpu.address |= ReadSNesMem(FULLPBRPC + 1) << 8;
   Cpu.address |= Cpu.PBR << 16;
   *(pu16)&Cpu.address += FULLX;
   Cpu.lo = ReadSNesMem(Cpu.address);
   Cpu.hi = ReadSNesMem(Cpu.address+1);
   MAKEPC(Cpu.lo, Cpu.hi);


pu16 = * unsigned short

The line: *(pu16)&Cpu.address += FULLX; is for handling wrap;
Is this ok?
Sorry i just want to be completly that what im doing is right....