A code object’s co_code holds its instructions one after another. Python’s
virtual machine is a stack machine: most instructions take values from a stack and
leave a result there. Below, TOS is the top of the stack, TOS1 the item under it, TOS2
the one under that.
Encoding
An instruction is one byte, the opcode, or three bytes when the opcode takes an
argument. Opcodes of 90 or more do; this dividing line is called
HAVE_ARGUMENT. The argument is an unsigned 16-bit little-endian number
directly after the opcode. So 7C 03 00 is LOAD_FAST 3 and
53 is RETURN_VALUE.
EXTENDED_ARG goes before an instruction whose argument does not fit in
two bytes. Its own argument becomes the high 16 bits of the next instruction’s
argument. Which opcode number it has depends on the release.
Arguments and jumps
What the argument means depends on the opcode.
LOAD_CONST: an index intoco_consts.STORE_NAME,DELETE_NAME,STORE_ATTR,DELETE_ATTR,STORE_GLOBAL,DELETE_GLOBAL,LOAD_NAME,LOAD_ATTR,IMPORT_NAME,IMPORT_FROM,LOAD_GLOBAL: an index intoco_names.LOAD_FAST,STORE_FAST,DELETE_FAST: an index intoco_varnames.LOAD_CLOSURE,LOAD_DEREF,STORE_DEREF: a slot in the cell and free variable storage. The name isco_cellvars[i], orco_freevars[i - len(co_cellvars)]onceiis past the cell variables.COMPARE_OP: an index into the table of comparison operators.
A jump’s argument is counted in bytes of co_code.
- Relative, counted from the instruction after the jump, so the target is the jump’s own offset, plus 3, plus the argument:
JUMP_FORWARD,FOR_ITER,SETUP_LOOP,SETUP_EXCEPT,SETUP_FINALLY, and, in 2.7,SETUP_WITH. Before 2.7,JUMP_IF_FALSEandJUMP_IF_TRUEare relative too. - Absolute, where the argument is the offset to go to:
JUMP_ABSOLUTE,CONTINUE_LOOP, and, in 2.7,JUMP_IF_FALSE_OR_POP,JUMP_IF_TRUE_OR_POP,POP_JUMP_IF_FALSEandPOP_JUMP_IF_TRUE.
Comparison operators
The argument of COMPARE_OP.
| Argument | Operator |
|---|---|
| 0 | < |
| 1 | <= |
| 2 | == |
| 3 | != |
| 4 | > |
| 5 | >= |
| 6 | in |
| 7 | not in |
| 8 | is |
| 9 | is not |
| 10 | exception match, for except clauses |
| 11 | BAD, the end of the list |
Every opcode
Numbers are from Lib/opcode.py at the tagged releases 2.3.7, 2.4.6, 2.5.6
and 2.6.9, and from a real 2.7 opcode.py. A dash means the release does
not have the opcode. Meanings follow Python’s dis documentation.
| Name | 2.3 | 2.4 | 2.5 | 2.6 | 2.7 | Meaning |
|---|---|---|---|---|---|---|
STOP_CODE | 0 | 0 | 0 | 0 | 0 | Marks the end of code for the compiler. The interpreter does not use it |
POP_TOP | 1 | 1 | 1 | 1 | 1 | Removes TOS |
ROT_TWO | 2 | 2 | 2 | 2 | 2 | Swaps the two top items |
ROT_THREE | 3 | 3 | 3 | 3 | 3 | Lifts the second and third items one place and moves the top down to third |
DUP_TOP | 4 | 4 | 4 | 4 | 4 | Duplicates the reference at TOS |
ROT_FOUR | 5 | 5 | 5 | 5 | 5 | Lifts the second, third and fourth items one place and moves the top down to fourth |
NOP | – | 9 | 9 | 9 | 9 | Does nothing. A placeholder for the bytecode optimiser |
UNARY_POSITIVE | 10 | 10 | 10 | 10 | 10 | TOS = +TOS |
UNARY_NEGATIVE | 11 | 11 | 11 | 11 | 11 | TOS = -TOS |
UNARY_NOT | 12 | 12 | 12 | 12 | 12 | TOS = not TOS |
UNARY_CONVERT | 13 | 13 | 13 | 13 | 13 | TOS = `TOS` (backticks: the value’s repr) |
UNARY_INVERT | 15 | 15 | 15 | 15 | 15 | TOS = ~TOS |
LIST_APPEND | – | 18 | 18 | 18 | 94 | Appends to a list, for list comprehensions. In 2.4 to 2.6 it has no argument and appends TOS to TOS1. In 2.7 it pops TOS and appends it to the list TOS[-i], where i is the argument |
BINARY_POWER | 19 | 19 | 19 | 19 | 19 | TOS = TOS1 ** TOS |
BINARY_MULTIPLY | 20 | 20 | 20 | 20 | 20 | TOS = TOS1 * TOS |
BINARY_DIVIDE | 21 | 21 | 21 | 21 | 21 | TOS = TOS1 / TOS when from __future__ import division is not in effect |
BINARY_MODULO | 22 | 22 | 22 | 22 | 22 | TOS = TOS1 % TOS |
BINARY_ADD | 23 | 23 | 23 | 23 | 23 | TOS = TOS1 + TOS |
BINARY_SUBTRACT | 24 | 24 | 24 | 24 | 24 | TOS = TOS1 - TOS |
BINARY_SUBSCR | 25 | 25 | 25 | 25 | 25 | TOS = TOS1[TOS] |
BINARY_FLOOR_DIVIDE | 26 | 26 | 26 | 26 | 26 | TOS = TOS1 // TOS |
BINARY_TRUE_DIVIDE | 27 | 27 | 27 | 27 | 27 | TOS = TOS1 / TOS when from __future__ import division is in effect |
INPLACE_FLOOR_DIVIDE | 28 | 28 | 28 | 28 | 28 | In-place TOS = TOS1 // TOS |
INPLACE_TRUE_DIVIDE | 29 | 29 | 29 | 29 | 29 | In-place TOS = TOS1 / TOS when from __future__ import division is in effect |
SLICE+0 | 30 | 30 | 30 | 30 | 30 | TOS = TOS[:] |
SLICE+1 | 31 | 31 | 31 | 31 | 31 | TOS = TOS1[TOS:] |
SLICE+2 | 32 | 32 | 32 | 32 | 32 | TOS = TOS1[:TOS] |
SLICE+3 | 33 | 33 | 33 | 33 | 33 | TOS = TOS2[TOS1:TOS] |
STORE_SLICE+0 | 40 | 40 | 40 | 40 | 40 | TOS[:] = TOS1 |
STORE_SLICE+1 | 41 | 41 | 41 | 41 | 41 | TOS1[TOS:] = TOS2 |
STORE_SLICE+2 | 42 | 42 | 42 | 42 | 42 | TOS1[:TOS] = TOS2 |
STORE_SLICE+3 | 43 | 43 | 43 | 43 | 43 | TOS2[TOS1:TOS] = TOS3 |
DELETE_SLICE+0 | 50 | 50 | 50 | 50 | 50 | del TOS[:] |
DELETE_SLICE+1 | 51 | 51 | 51 | 51 | 51 | del TOS1[TOS:] |
DELETE_SLICE+2 | 52 | 52 | 52 | 52 | 52 | del TOS1[:TOS] |
DELETE_SLICE+3 | 53 | 53 | 53 | 53 | 53 | del TOS2[TOS1:TOS] |
STORE_MAP | – | – | – | 54 | 54 | Stores a key and value pair in a dictionary. Pops the key and value and leaves the dictionary on the stack |
INPLACE_ADD | 55 | 55 | 55 | 55 | 55 | In-place TOS = TOS1 + TOS |
INPLACE_SUBTRACT | 56 | 56 | 56 | 56 | 56 | In-place TOS = TOS1 - TOS |
INPLACE_MULTIPLY | 57 | 57 | 57 | 57 | 57 | In-place TOS = TOS1 * TOS |
INPLACE_DIVIDE | 58 | 58 | 58 | 58 | 58 | In-place TOS = TOS1 / TOS when from __future__ import division is not in effect |
INPLACE_MODULO | 59 | 59 | 59 | 59 | 59 | In-place TOS = TOS1 % TOS |
STORE_SUBSCR | 60 | 60 | 60 | 60 | 60 | TOS1[TOS] = TOS2 |
DELETE_SUBSCR | 61 | 61 | 61 | 61 | 61 | del TOS1[TOS] |
BINARY_LSHIFT | 62 | 62 | 62 | 62 | 62 | TOS = TOS1 << TOS |
BINARY_RSHIFT | 63 | 63 | 63 | 63 | 63 | TOS = TOS1 >> TOS |
BINARY_AND | 64 | 64 | 64 | 64 | 64 | TOS = TOS1 & TOS |
BINARY_XOR | 65 | 65 | 65 | 65 | 65 | TOS = TOS1 ^ TOS |
BINARY_OR | 66 | 66 | 66 | 66 | 66 | TOS = TOS1 | TOS |
INPLACE_POWER | 67 | 67 | 67 | 67 | 67 | In-place TOS = TOS1 ** TOS |
GET_ITER | 68 | 68 | 68 | 68 | 68 | TOS = iter(TOS) |
PRINT_EXPR | 70 | 70 | 70 | 70 | 70 | The expression statement in interactive mode: removes TOS and prints it |
PRINT_ITEM | 71 | 71 | 71 | 71 | 71 | Prints TOS, one per item of a print statement |
PRINT_NEWLINE | 72 | 72 | 72 | 72 | 72 | Prints a new line. Ends a print statement that does not end with a comma |
PRINT_ITEM_TO | 73 | 73 | 73 | 73 | 73 | As PRINT_ITEM, but prints the item below TOS to the file at TOS (print >>f) |
PRINT_NEWLINE_TO | 74 | 74 | 74 | 74 | 74 | As PRINT_NEWLINE, on the file at TOS |
INPLACE_LSHIFT | 75 | 75 | 75 | 75 | 75 | In-place TOS = TOS1 << TOS |
INPLACE_RSHIFT | 76 | 76 | 76 | 76 | 76 | In-place TOS = TOS1 >> TOS |
INPLACE_AND | 77 | 77 | 77 | 77 | 77 | In-place TOS = TOS1 & TOS |
INPLACE_XOR | 78 | 78 | 78 | 78 | 78 | In-place TOS = TOS1 ^ TOS |
INPLACE_OR | 79 | 79 | 79 | 79 | 79 | In-place TOS = TOS1 | TOS |
BREAK_LOOP | 80 | 80 | 80 | 80 | 80 | Ends a loop, for a break statement |
WITH_CLEANUP | – | – | 81 | 81 | 81 | Cleans up the stack when a with block exits and calls the context manager’s __exit__ |
LOAD_LOCALS | 82 | 82 | 82 | 82 | 82 | Pushes the local namespace. Used at the end of a class body |
RETURN_VALUE | 83 | 83 | 83 | 83 | 83 | Returns TOS to the caller |
IMPORT_STAR | 84 | 84 | 84 | 84 | 84 | Copies every name not starting with _ from the module at TOS into the local namespace, then pops the module (from m import *) |
EXEC_STMT | 85 | 85 | 85 | 85 | 85 | exec TOS2, TOS1, TOS. The compiler fills in missing arguments with None |
YIELD_VALUE | 86 | 86 | 86 | 86 | 86 | Pops TOS and yields it from a generator |
POP_BLOCK | 87 | 87 | 87 | 87 | 87 | Removes one block from the block stack |
END_FINALLY | 88 | 88 | 88 | 88 | 88 | Ends a finally clause. The interpreter re-raises the exception, returns or goes on, as it had recorded |
BUILD_CLASS | 89 | 89 | 89 | 89 | 89 | Makes a class: TOS is the methods dictionary, TOS1 the tuple of base classes, TOS2 the name |
STORE_NAME | 90 | 90 | 90 | 90 | 90 | name = TOS. The argument is an index into co_names |
DELETE_NAME | 91 | 91 | 91 | 91 | 91 | del name. The argument is an index into co_names |
UNPACK_SEQUENCE | 92 | 92 | 92 | 92 | 92 | Unpacks TOS into the given number of values, pushed right to left |
FOR_ITER | 93 | 93 | 93 | 93 | 93 | TOS is an iterator. Calls its next(). A new value is pushed, with the iterator left below it. When exhausted, TOS is popped and the byte counter moves on by the argument |
STORE_ATTR | 95 | 95 | 95 | 95 | 95 | TOS.name = TOS1. The argument is an index into co_names |
DELETE_ATTR | 96 | 96 | 96 | 96 | 96 | del TOS.name. The argument is an index into co_names |
STORE_GLOBAL | 97 | 97 | 97 | 97 | 97 | As STORE_NAME, but stores a global |
DELETE_GLOBAL | 98 | 98 | 98 | 98 | 98 | As DELETE_NAME, but deletes a global |
DUP_TOPX | 99 | 99 | 99 | 99 | 99 | Duplicates the top items, keeping their order. The argument is how many, from 1 to 5 |
LOAD_CONST | 100 | 100 | 100 | 100 | 100 | Pushes co_consts[argument] |
LOAD_NAME | 101 | 101 | 101 | 101 | 101 | Pushes the value of co_names[argument] |
BUILD_TUPLE | 102 | 102 | 102 | 102 | 102 | Pops the given number of items and pushes them as a tuple |
BUILD_LIST | 103 | 103 | 103 | 103 | 103 | As BUILD_TUPLE, but makes a list |
BUILD_SET | – | – | – | – | 104 | As BUILD_TUPLE, but makes a set |
BUILD_MAP | 104 | 104 | 104 | 104 | 105 | Pushes a new dictionary. In 2.7 the argument is the number of entries to size it for; the argument of the older form was ignored |
LOAD_ATTR | 105 | 105 | 105 | 105 | 106 | Replaces TOS with getattr(TOS, co_names[argument]) |
COMPARE_OP | 106 | 106 | 106 | 106 | 107 | Compares TOS1 with TOS. The argument indexes the operators |
IMPORT_NAME | 107 | 107 | 107 | 107 | 108 | Imports the module co_names[argument] and pushes it. In 2.7, TOS and TOS1 are popped and give the fromlist and level arguments. The namespace is not changed; a following store does that |
IMPORT_FROM | 108 | 108 | 108 | 108 | 109 | Loads the attribute co_names[argument] from the module at TOS and pushes it, for a following store |
JUMP_FORWARD | 110 | 110 | 110 | 110 | 110 | Moves the byte counter on by the argument |
JUMP_IF_FALSE | 111 | 111 | 111 | 111 | – | If TOS is false, moves the byte counter on by the argument. TOS is left on the stack |
JUMP_IF_FALSE_OR_POP | – | – | – | – | 111 | If TOS is false, sets the byte counter to the argument and leaves TOS on the stack. Otherwise TOS is popped |
JUMP_IF_TRUE | 112 | 112 | 112 | 112 | – | If TOS is true, moves the byte counter on by the argument. TOS is left on the stack |
JUMP_IF_TRUE_OR_POP | – | – | – | – | 112 | If TOS is true, sets the byte counter to the argument and leaves TOS on the stack. Otherwise TOS is popped |
JUMP_ABSOLUTE | 113 | 113 | 113 | 113 | 113 | Sets the byte counter to the argument |
POP_JUMP_IF_FALSE | – | – | – | – | 114 | If TOS is false, sets the byte counter to the argument. TOS is popped |
POP_JUMP_IF_TRUE | – | – | – | – | 115 | If TOS is true, sets the byte counter to the argument. TOS is popped |
LOAD_GLOBAL | 116 | 116 | 116 | 116 | 116 | Pushes the global co_names[argument] |
CONTINUE_LOOP | 119 | 119 | 119 | 119 | 119 | Continues a loop, for a continue statement. The argument is the address to jump to |
SETUP_LOOP | 120 | 120 | 120 | 120 | 120 | Pushes a loop block. The block is the argument’s size in bytes from the current instruction |
SETUP_EXCEPT | 121 | 121 | 121 | 121 | 121 | Pushes a try block. The argument points to the first except block |
SETUP_FINALLY | 122 | 122 | 122 | 122 | 122 | Pushes a try block. The argument points to the finally block |
LOAD_FAST | 124 | 124 | 124 | 124 | 124 | Pushes the local variable co_varnames[argument] |
STORE_FAST | 125 | 125 | 125 | 125 | 125 | Stores TOS into the local variable co_varnames[argument] |
DELETE_FAST | 126 | 126 | 126 | 126 | 126 | Deletes the local variable co_varnames[argument] |
RAISE_VARARGS | 130 | 130 | 130 | 130 | 130 | Raises an exception. The argument is how many arguments the raise statement gave, up to three: the traceback at TOS2, the value at TOS1, the exception at TOS |
CALL_FUNCTION | 131 | 131 | 131 | 131 | 131 | Calls a function. The low byte of the argument is the number of positional arguments, the high byte the number of keyword arguments. On the stack: keyword pairs, the value above each key, then the positional arguments with the rightmost on top, then the function. All are popped and the result is pushed |
MAKE_FUNCTION | 132 | 132 | 132 | 132 | 132 | Pushes a new function. TOS is its code. The argument is how many default values lie below it |
BUILD_SLICE | 133 | 133 | 133 | 133 | 133 | Pushes a slice. With argument 2 it is slice(TOS1, TOS); with 3, slice(TOS2, TOS1, TOS) |
MAKE_CLOSURE | 134 | 134 | 134 | 134 | 134 | Pushes a new function with a closure. TOS is its code and the cells for its free variables come next. The argument is how many default values lie below the cells |
LOAD_CLOSURE | 135 | 135 | 135 | 135 | 135 | Pushes the cell in the given slot of the cell and free variable storage |
LOAD_DEREF | 136 | 136 | 136 | 136 | 136 | Pushes the object held by the cell in the given slot |
STORE_DEREF | 137 | 137 | 137 | 137 | 137 | Stores TOS into the cell in the given slot |
CALL_FUNCTION_VAR | 140 | 140 | 140 | 140 | 140 | As CALL_FUNCTION; TOS is the iterable of extra positional arguments |
CALL_FUNCTION_KW | 141 | 141 | 141 | 141 | 141 | As CALL_FUNCTION; TOS is the mapping of extra keyword arguments |
CALL_FUNCTION_VAR_KW | 142 | 142 | 142 | 142 | 142 | As CALL_FUNCTION; TOS is the mapping of keyword arguments and below it the iterable of positional arguments |
SETUP_WITH | – | – | – | – | 143 | Starts a with block: loads __exit__() for later, calls __enter__(), pushes a finally block pointing to the argument and pushes the result |
EXTENDED_ARG | 143 | 143 | 143 | 143 | 145 | Gives the next instruction the high 16 bits of its argument |
SET_ADD | – | – | – | – | 146 | Used in set comprehensions. Pops TOS and adds it to the set found using the argument |
MAP_ADD | – | – | – | – | 147 | Used in dictionary comprehensions. Pops a key (TOS) and value (TOS1) and adds them to the dictionary found using the argument |