With a given bytecode, when encountering a switch
instruction, I want to know where the next instruction is (without running the code). In order to do that, I was thinking that I should calculate the total size of the instruction, including jump offsets or match-offset pairs. Is this possible? If it is not, how is it possible to know where the next instruction is?
Also, are there any other bytecode instructions with dynamic sizes (their sizes based on a variable)?
tableswitch
<0-3 byte pad>
defaultbyte1
defaultbyte2
defaultbyte3
defaultbyte4
lowbyte1
lowbyte2
lowbyte3
lowbyte4
highbyte1
highbyte2
highbyte3
highbyte4
jump offsets...
lookupswitch
<0-3 byte pad>
defaultbyte1
defaultbyte2
defaultbyte3
defaultbyte4
npairs1
npairs2
npairs3
npairs4
match-offset pairs...
You'll need to read the values of high
and low
(for tableswitch
) and the value of npairs
(for loopkupswitch
).
Also, defaultbyte1
always begins at an address that is a multiple of four bytes from the start of the current method. A padding between 0
and 3
bytes is needed immediately after the opcode.
The length of tableswitch
is equal to 1 for the opcode + up to 3 bytes for padding + 4 bytes for the default jump offset + 4 bytes for high
+ 4 bytes for low
+ 4 bytes for each jump offset (there are high-low+1
of them). In total:
1 + p + 4 + 4 + 4 + 4*(high-low+1)
where p
is the padding between 0
and 3
.
The length of lookupswitch
is equal to 1 byte for the opcode + up to 3 bytes for padding + 4 bytes for the default jump offset + 4 bytes for the number of pairs (npairs
) + 8 bytes for each pair of match
and jump offset. In total:
1 + p + 4 + 4 + 8*(npairs)
where p
is the padding between 0
and 3
.
There is another instruction wide
where its length can be either 4 or 6 bytes. If the following opcode is iinc
, then length is 6. Otherwise, it's 4.