lookupswitch <key1> : <label1> <key2> : <label2> ... <keyN> : <labelN> default : <labelDefault><key1>, <key2> etc. are 32-bit integers. <label1>, <label2>, etc. are label names.
To define the location of the label, use the <label> name followed by a colon:
<label>:<label> then becomes associated the address of the following instruction. Labels can only be assigned one location in a method. On the other hand, a single <label> can be the target of multiple branch instructions.
Stack Before
Description After item ... ...
This is used to perform an efficient compare-and-jump, as might be needed for a switch statement. The table used by lookupswitch is given after the lookupswitch opcode in bytecode.
lookupswitch works as follows. First, an int, item, is taken from the top of the stack. Then, lookupswitch searches the table looking for an entry whose <key> field matches item. If a match is found, execution branches to the address of the corresponding <label>. If no match is found, execution branches to <labelDefault>.
Example
; this is like the Java code: ; switch (i) { ; case 1: return(10); ; case 10: return(100); ; default: return(0); ; } iload_1 ; push local variable 1 onto the stack (i.e. i) ; switch based on the value on the stack lookupswitch 1 : Label1 10 : Label2 default : Dlabel Label1: ; local variable 1 holds the value 1 bipush 10 ireturn ; return 10 Label2: ; local variable 1 holds the value 10 bipush 100 ireturn ; return 100 Dlabel: ; local variable 1 holds something else bipush 0 return ; return 0Bytecode
lookupswitch is a variable length instruction. After the lookupswitch opcode, between 0 to 3 bytes of padding zeros are inserted, so that the default_offset parameter starts at an offset in the bytecode which is a multiple of 4. Next, a 32-bit int n >= 0 is given, indicating the number of key/value integer pairs in the table. This is followed by n pairs of ints. For each pair, the first 32-bit int value is the key, and the second 32-bit int value is the relative offset to jump to if that key is matched. (the offset is relative to the address of the lookupswitch instruction in bytecode).
Type | Description |
u1 | lookupswitch opcode = 0xAB (171) |
- | ...0-3 bytes of padding ... |
s4 | default_offset |
s4 | n |
s4 | key_1 |
s4 | offset_1 |
s4 | key_2 |
s4 | offset_2 |
... | ... |
s4 | key_n |
s4 | offset_n |
tableswitch
Notes
1. Addresses are measured in bytes from the start of the bytecode (i.e. address 0 is the first byte in the bytecode of the currently executing method).
2. Addresses given in the table are relative - the values in the table are added to the current pc (i.e. the address of this lookupswitch instruction) to obtain the new value for pc.
3. Keys in the table must be sorted in increasing order, so <key1> is less than <key2>, and so on up to <keyN>. Jasmin performs this sorting automatically.
4. Even though offsets in the table are given as 32-bit ints, the maximum address in a Java method is limited by other factors to 65535.