## Z80 jump table

Moderator: BigEvilCorporation

Sik
Very interested
Posts: 845
Joined: Thu Apr 10, 2008 3:03 pm
Contact:

### Z80 jump table

Just noticed you can do this to get a jump table on the Z80 (probably an old trick and I'm being a newbie, but whatever):

Code: Select all

``````; a = index (0..42)
; b = spare

ld      b, a            ; Multiply index by 3
ld      (\$+4), a        ; Overwrite the jump destination
jr      \$               ; Jump to the table

jp      Routine1
jp      Routine2
jp      Routine3
...``````
This relies on self-modifying code (it overwrites a jump), so you need to run this off RAM, but that's usually the case on the Mega Drive so no biggie. Also the index is quite limited due to overflow (maximum that works is 42), but it still should be large enough for most purposes. Beats having to do 16-bit arithmetic on an address when you can't ensure a table will be within a 256 byte boundary.

I'm multiplying the index by 3 since that's how long a JP instruction is (I'm assuming that the targets may be anywhere). If you can really ensure that all target addresses are close enough (within around 127 bytes*) then it'd look more like this:

Code: Select all

``````; a = index (0..63)

add     a, a            ; Multiply index by 2
ld      (\$+4), a        ; Overwrite the jump destination
jr      \$               ; Jump to the table

jr      Routine1
jr      Routine2
jr      Routine3
...``````
By the way, the \$ in that jump is just a placeholder (it'll be overwritten), I just picked something that would be within the allowed range so it can assemble.

*I say "around" since it needs to be 127 bytes away from the specific jump, so the actual maximum distance from the start of the code depends on which entry is being jumped to. Still should give a good idea of how far away it can afford to be.
Sik is pronounced as "seek", not as "sick".

HardWareMan
Very interested
Posts: 726
Joined: Sat Dec 15, 2007 7:49 am
Location: Kazakhstan, Pavlodar

### Re: Z80 jump table

Z80 have jp (hl). Just a hint.
Last edited by HardWareMan on Tue Mar 20, 2018 7:23 am, edited 1 time in total.

Stef
Very interested
Posts: 2948
Joined: Thu Nov 30, 2006 9:46 pm
Location: France - Sevres
Contact:

### Re: Z80 jump table

What i'm doing in my XGM driver :

Code: Select all

``````    LD    A, (DE)             ; A = command           ' 7     |
LD    (.ld_hl_xx + 1), A  ; set jump address      ' 13    |

.ld_hl_xx
LD    HL, (JUMP_TABLE)    ; LD HL, (jt)           ' 16    |
JP   (HL)                    ;             ' 4 |
``````
Note that compiled XGM always encode command shifted by one (<<= 1) to save some cycles here but that reduce number of entries to 0x80.

Sik
Very interested
Posts: 845
Joined: Thu Apr 10, 2008 3:03 pm
Contact:

### Re: Z80 jump table

HardWareMan wrote:
Mon Mar 19, 2018 6:35 am
Z80 have jr (hl). Just a hint.
You mean JP :v

But anyway, using that would then require 16-bit operations to calculate the address which is like the whole thing I was trying to avoid (as it starts getting cumbersome). Either that or ensuring the table never crosses a 256 byte boundary (which is not always worth it, as you need to do lots of juggling regarding where you put those tables in the code, so better leave that for stuff you may need to access a lot or the like).
Stef wrote:
Mon Mar 19, 2018 9:09 am
Note that compiled XGM always encode command shifted by one (<<= 1) to save some cycles here but that reduce number of entries to 0x80.
Yeah, for speed critical stuff it may be better to store the index multiplied by the entry size already.
Sik is pronounced as "seek", not as "sick".

HardWareMan
Very interested
Posts: 726
Joined: Sat Dec 15, 2007 7:49 am
Location: Kazakhstan, Pavlodar

### Re: Z80 jump table

Sik wrote:
Tue Mar 20, 2018 5:15 am
HardWareMan wrote:
Mon Mar 19, 2018 6:35 am
Z80 have jr (hl). Just a hint.
You mean JP :v
I mean PCHL since I don't like Z80 mnemonics.

### Who is online

Users browsing this forum: No registered users and 2 guests