dis — Диссеблер для байткода Python
Исходный код: Lib/dis.py
Модуль dis поддерживает анализ байткода CPython, дизассемблируя его. Байткод CPython, который принимает этот модуль на вход, определен в файле Include/opcode.h и используется компилятором и интерпретатором.
Деталь реализации CPython: Байткод — это деталь реализации интерпретатора CPython. Не гарантируется, что байткод не будет добавлен, удален или изменён между версиями Python. Использование этого модуля не должно рассматриваться как работающее в разных виртуальных машинах Python или разных версиях Python.
Изменено в версии 3.6: Используются 2 байта для каждой инструкции. Ранее количество байтов варьировалось в зависимости от инструкции.
Изменено в версии 3.10: Аргумент инструкций перехода, обработки исключений и циклов теперь представляет собой смещение инструкции, а не смещение байта.
Изменено в версии 3.11: Некоторые инструкции сопровождаются одной или несколькими записями кэша встраивания, которые имеют вид инструкций CACHE. Эти инструкции по умолчанию скрыты, но могут быть показаны, передав show_caches=True любому инструменту dis. Кроме того, интерпретатор теперь адаптирует байткод для специализации его под различные условия выполнения. Адаптированный байткод можно отобразить, передав adaptive=True.
Изменено в версии 3.12: Аргумент инструкции перехода — смещение целевой инструкции относительно инструкции, которая следует сразу после записей инструкции перехода CACHE.
Вследствие этого, наличие инструкций CACHE прозрачно для переходов вперёд, но необходимо учитывать их при размышлении о переходах назад.
Пример: Для функции myfunc():
def myfunc(alist):
return len(alist)
следующая команда может быть использована для отображения дизассемблирования myfunc():
>>> dis.dis(myfunc)
2 0 RESUME 0
3 2 LOAD_GLOBAL 1 (NULL + len)
12 LOAD_FAST 0 (alist)
14 CALL 1
22 RETURN_VALUE
(Число «2» — номер строки).
Интерфейс командной строки
Модуль dis может быть вызван как скрипт из командной строки:
python -m dis [-h] [infile]
Принимаются следующие параметры:
-
-h, --help -
Отобразить использование и выйти.
Если infile указан, его дизассемблированный код будет выведен в стандартный поток вывода. В противном случае дизассемблирование выполняется над скомпилированным исходным кодом, полученным со стандартного потока ввода.
Анализ байткода
Добавлен в версии 3.4.
API анализа байткода позволяет обернуть фрагменты кода Python в объект Bytecode, который предоставляет удобный доступ к деталям скомпилированного кода.
-
class dis.Bytecode(x, *, first_line=None, current_offset=None, show_caches=False, adaptive=False) -
Анализирует байткод, соответствующий функции, генератору, асинхронному генератору, корутине, методу, строке исходного кода или объекту кода (возвращаемому
compile()).Это удобная обертка вокруг многих функций, перечисленных ниже, в первую очередь
get_instructions(), так как итерация по экземпляруBytecodeвозвращает операции байткода в виде экземпляровInstruction.Если first_line не
None, это указывает номер строки, который должен быть отображён для первой строки исходного кода в дизассемблированном коде. В противном случае информация о строках исходного кода (если таковая имеется) берётся непосредственно из объекта дизассемблированного кода.Если current_offset не
None, это относится к смещению инструкции в дизассемблированном коде. Установка этого значения означает, чтоdis()отобразит маркер «текущая инструкция» для указанной операции.Если show_caches
True,dis()отобразит записи кэша встраивания, используемые интерпретатором для специализации байткода.Если adaptive
True,dis()отобразит специализированный байткод, который может отличаться от исходного байткода.-
classmethod from_traceback(tb, *, show_caches=False) -
Создаёт экземпляр
Bytecodeиз заданного отслеживания исключений, устанавливая current_offset на инструкцию, ответсвенную за исключение.
-
codeobj -
Объект скомпилированного кода.
-
first_line -
Первая строка исходного кода объекта (если доступна)
-
dis() -
Возвращает отформатированный вид операций байткода (тот же, что и выводится
dis.dis(), но возвращается как многострочная строка).
-
info() -
Возвращает отформатированную многострочную строку с подробной информацией об объекте кода, подобно
code_info().
Изменено в версии 3.7: Теперь может обрабатывать объекты корутин и асинхронных генераторов.
Изменено в версии 3.11: Добавлены параметры show_caches и adaptive.
-
Пример:
>>> bytecode = dis.Bytecode(myfunc) >>> for instr in bytecode: ... print(instr.opname) ... RESUME LOAD_GLOBAL LOAD_FAST CALL RETURN_VALUE
Функции анализа
Модуль dis также определяет следующие функции анализа, которые преобразуют входные данные непосредственно в желаемый вывод. Они могут быть полезны, если выполняется только одна операция, поэтому промежуточный объект анализа не нужен:
-
dis.code_info(x) -
Возвращает отформатированную строку с несколькими строками и подробной информацией об объекте кода для переданной функции, генератора, асинхронного генератора, корутины, метода, строки исходного кода или объекта кода.
Обратите внимание, что точное содержимое строк с информацией о коде сильно зависит от реализации и может произвольно изменяться между различными виртуальными машинами Python или версиями Python.
Добавлена в версии 3.2.
Изменено в версии 3.7: Теперь может обрабатывать объекты корутин и асинхронных генераторов.
-
dis.show_code(x, *, file=None) -
Выводит подробную информацию об объекте кода для переданной функции, метода, строки исходного кода или объекта кода в file (или
sys.stdoutесли file не указан).Это удобное сокращение для
print(code_info(x), file=file), предназначенное для интерактивного исследования в командной строке интерпретатора.Добавлена в версии 3.2.
Изменено в версии 3.4: Добавлен параметр file.
-
dis.dis(x=None, *, file=None, depth=None, show_caches=False, adaptive=False) -
Разобрать объект x. x может обозначать модуль, класс, метод, функцию, генератор, асинхронный генератор, корутину, объект кода, строку исходного кода или последовательность байтов исходного байткода. Для модуля он разбирает все функции. Для класса он разбирает все методы (включая методы класса и статические методы). Для объекта кода или последовательности исходного байткода он выводит по одной строке на инструкцию байткода. Он также рекурсивно разбирает вложенные объекты кода. Это могут включать выражения генератора, вложенные функции, тела вложенных классов и объекты кода, используемые для областей аннотаций. Строки сначала компилируются в объекты кода с помощью встроенной функции
compile()перед разборкой. Если объект не предоставлен, эта функция разбирает последний стек отслеживания.Разборка записывается в текстовом формате в переданный аргумент file, если он предоставлен, и в
sys.stdoutв противном случае.Максимальная глубина рекурсии ограничена depth, если она не
None.depth=0означает отсутствие рекурсии.Если show_caches
True, эта функция отобразит записи кеша inline, используемые интерпретатором для специализации байткода.Если adaptive
True, эта функция отобразит специализированный байт код, который может отличаться от исходного байткода.Изменено в версии 3.4: Добавлен параметр file.
Изменено в версии 3.7: Реализована рекурсивная разборка и добавлен параметр depth.
Изменено в версии 3.7: Теперь может обрабатывать объекты корутин и асинхронных генераторов.
Изменено в версии 3.11: Добавлены параметры show_caches и adaptive.
-
dis.distb(tb=None, *, file=None, show_caches=False, adaptive=False) -
Разбирает функцию в вершине стека стека отслеживания, используя последний стек отслеживания, если он не был передан. Указана инструкция, вызвавшая исключение.
Разборка записывается в текстовом формате в переданный аргумент file, если он предоставлен, и в
sys.stdoutв противном случае.Изменено в версии 3.4: Добавлен параметр file.
Изменено в версии 3.11: Добавлены параметры show_caches и adaptive.
-
dis.disassemble(code, lasti=-1, *, file=None, show_caches=False, adaptive=False) -
dis.disco(code, lasti=-1, *, file=None, show_caches=False, adaptive=False) -
Разбирает объект кода, указывая последнюю инструкцию, если был предоставлен lasti. Вывод разделен на следующие столбцы:
- номер строки, для первой инструкции каждой строки
- текущая инструкция, указанная как
-->, - метки инструкции, указанные с
>>, - адрес инструкции,
- имя кода операции,
- параметры операции и
- интерпретация параметров в скобках.
Интерпретация параметров распознает имена локальных и глобальных переменных, значения констант, целевые адреса ветвления и операторы сравнения.
Разборка записывается в текстовом формате в переданный аргумент file, если он предоставлен, и в
sys.stdoutв противном случае.Изменено в версии 3.4: Добавлен параметр file.
Изменено в версии 3.11: Добавлены параметры show_caches и adaptive.
-
dis.get_instructions(x, *, first_line=None, show_caches=False, adaptive=False) -
Возвращает итератор по инструкциям в переданной функции, методе, строке исходного кода или объекте кода.
Итератор генерирует серию именованных кортежей
Instruction, предоставляющих подробную информацию о каждой операции в переданном коде.Если first_line не
None, он указывает номер строки, который должен быть выведен для первой строки исходного кода в разобранном коде. В противном случае информация о строках исходного кода (если она есть) берется непосредственно из разобранного объекта кода.Параметры show_caches и adaptive работают так же, как и в
dis().Добавлена в версии 3.4.
Изменено в версии 3.11: Добавлены параметры show_caches и adaptive.
-
dis.findlinestarts(code) -
Эта функция-генератор использует метод
co_lines()объекта объекта кода code для поиска смещений, которые являются началом строк в исходном коде. Они генерируются как пары(offset, lineno).Изменено в версии 3.6: Номера строк могут быть убывающими. Раньше они всегда были возрастающими.
Изменено в версии 3.10: Вместо атрибутов
co_firstlinenoиco_lnotabобъекта объекта кода используется методco_lines()PEP 626.
-
dis.findlabels(code) -
Обнаруживает все смещения в строке исходного байткода code, которые являются целевыми адресами переходов, и возвращает список этих смещений.
-
dis.stack_effect(opcode, oparg=None, *, jump=None) -
Вычисляет эффект стека для opcode с аргументом oparg.
Если в коде есть целевой адрес перехода и jump
True,stack_effect()вернет эффект стека при переходе. Если jumpFalse, он вернет эффект стека при отсутствии перехода. А если jumpNone(по умолчанию), он вернет максимальный эффект стека в обоих случаях.Добавлена в версии 3.4.
Изменено в версии 3.8: Добавлен параметр jump.
Инструкции байткода Python
Функция get_instructions() и класс Bytecode предоставляют подробности о инструкциях байткода в виде экземпляров Instruction:
-
class dis.Instruction -
Подробности для операции байткода
-
opcode -
Числовой код операции, соответствующий значениям opcode, перечисленным ниже, и значениям байткода в Коллекциях opcode.
-
opname -
Человекопонятное имя операции
-
arg -
Числовой аргумент операции (если есть), в противном случае
None
-
argval -
Разрешенное значение аргумента (если есть), в противном случае
None
-
argrepr -
Человекопонятное описание аргумента операции (если есть), в противном случае пустая строка.
-
offset -
Начальный индекс операции в последовательности байткода
-
starts_line -
Строка, начинающаяся с этого opcode (если есть), в противном случае
None
-
is_jump_target -
Trueесли другая часть кода переходит сюда, в противном случаеFalse
-
positions -
Объект
dis.Positions, содержащий начальные и конечные позиции, которые охватываются этой инструкцией.
Добавлен в версии 3.4.
Изменено в версии 3.11: Добавленное поле
positions. -
-
class dis.Positions -
В случае отсутствия информации некоторые поля могут быть
None.-
lineno
-
end_lineno
-
col_offset
-
end_col_offset
Добавлен в версии 3.11.
-
В настоящее время компилятор Python генерирует следующие инструкции байткода.
Общие инструкции
В дальнейшем мы будем ссылаться на стек интерпретатора как на STACK и описывать операции с ним, как если бы это был список Python. Вершина стека соответствует STACK[-1] в этом языке.
-
NOP -
Инструкция ничего не делает. Используется в качестве заполнителя оптимизатором байткода и для генерации событий отслеживания строк.
-
POP_TOP -
Удаляет элемент с вершины стека:
STACK.pop()
-
END_FOR -
Удаляет верхние два значения из стека. Эквивалентно
POP_TOP;POP_TOP. Используется для очистки по окончании циклов, отсюда и название.Добавлен в версии 3.12.
-
END_SEND -
Реализует
del STACK[-2]. Используется для очистки при выходе генератора.Добавлен в версии 3.12.
-
COPY(i) -
Поместить i-й элемент на вершину стека без удаления его из исходного местоположения:
assert i > 0 STACK.append(STACK[-i])
Добавлен в версии 3.11.
-
SWAP(i) -
Поменять местами верхний элемент стека с i-м элементом:
STACK[-i], STACK[-1] = STACK[-1], STACK[-i]
Добавлен в версии 3.11.
-
CACHE -
Вместо того, чтобы быть реальной инструкцией, этот opcode используется для обозначения дополнительного места для кэширования интерпретатором полезных данных непосредственно в самом байткоде. Он автоматически скрывается всеми
disутилитами, но может быть просмотрен с помощьюshow_caches=True.Логически это пространство является частью предыдущей инструкции. Многие opcode ожидают, что за ними следует точное количество кэшей, и будут инструктировать интерпретатор пропустить их во время выполнения.
Заполненные кэши могут выглядеть как произвольные инструкции, поэтому следует проявлять осторожность при чтении или модификации исходного адаптивного байткода, содержащего ускоренные данные.
Добавлен в версии 3.11.
Унарные операции
Унарные операции берут верхний элемент стека, применяют операцию и возвращают результат обратно на стек.
-
UNARY_NEGATIVE -
Реализует
STACK[-1] = -STACK[-1].
-
UNARY_NOT -
Реализует
STACK[-1] = not STACK[-1].
-
UNARY_INVERT -
Реализует
STACK[-1] = ~STACK[-1].
-
GET_ITER -
Реализует
STACK[-1] = iter(STACK[-1]).
-
GET_YIELD_FROM_ITER -
Если
STACK[-1]— объект генератор итератор или корутина, он остается без изменений. В противном случае, реализуетSTACK[-1] = iter(STACK[-1]).Добавлен в версии 3.5.
Бинарные и операции со ссылочной целостностью
Бинарные операции удаляют два верхних элемента из стека (STACK[-1] и STACK[-2]). Выполняют операцию, а затем помещают результат обратно на стек.
Операции со ссылочной целостностью аналогичны бинарным операциям, но операция выполняется непосредственно, если STACK[-2] её поддерживает, и результат STACK[-1] может (но не обязательно) быть исходным STACK[-2].
-
BINARY_OP(op) -
Реализует бинарные и операции со ссылочной целостностью (в зависимости от значения op):
rhs = STACK.pop() lhs = STACK.pop() STACK.append(lhs op rhs)
Добавлен в версии 3.11.
-
BINARY_SUBSCR -
Реализует:
key = STACK.pop() container = STACK.pop() STACK.append(container[key])
-
STORE_SUBSCR -
Реализует:
key = STACK.pop() container = STACK.pop() value = STACK.pop() container[key] = value
-
DELETE_SUBSCR -
Реализует:
key = STACK.pop() container = STACK.pop() del container[key]
-
BINARY_SLICE -
Реализует:
end = STACK.pop() start = STACK.pop() container = STACK.pop() STACK.append(container[start:end])
Добавлен в версии 3.12.
-
STORE_SLICE -
Реализует:
end = STACK.pop() start = STACK.pop() container = STACK.pop() values = STACK.pop() container[start:end] = value
Добавлен в версии 3.12.
Инструкции корутины
-
GET_AWAITABLE(where) -
Реализует
STACK[-1] = get_awaitable(STACK[-1]), гдеget_awaitable(o)возвращаетoеслиo— объект корутины или генератор с флагомCO_ITERABLE_COROUTINE, или разрешаетo.__await__.Если операнд
whereне равен нулю, он указывает, где находится инструкция:-
1: После вызова__aenter__ -
2: После вызова__aexit__
Добавлен в версии 3.5.
Изменено в версии 3.11: Ранее у этой инструкции не было oparg.
-
-
GET_AITER -
Реализует
STACK[-1] = STACK[-1].__aiter__().Добавлена в версии 3.5.
Изменено в версии 3.7: Возврат объектов, ожидающих выполнения, из
__aiter__больше не поддерживается.
-
GET_ANEXT -
Реализует
STACK.append(get_awaitable(STACK[-1].__anext__()))в стек. Подробности оget_awaitableсм. вGET_AWAITABLE.Добавлена в версии 3.5.
-
END_ASYNC_FOR -
Завершает цикл
async for. Обрабатывает исключение, поднятое при ожидании следующего элемента. В стеке находится асинхронный итерируемый объект вSTACK[-2]и поднятое исключение вSTACK[-1]. Оба извлекаются. Если исключение не являетсяStopAsyncIteration, оно переиздаётся.Добавлена в версии 3.8.
Изменено в версии 3.11: Представление исключения в стеке теперь состоит из одного, а не трёх элементов.
-
CLEANUP_THROW -
Обрабатывает исключение, поднятое во время вызова
throw()илиclose()через текущий фрейм. ЕслиSTACK[-1]является экземпляромStopIteration, извлекает три значения из стека и помещает его членvalue. В противном случае, переиздаётSTACK[-1].Добавлена в версии 3.12.
-
BEFORE_ASYNC_WITH -
Решает
__aenter__и__aexit__изSTACK[-1]. Помещает__aexit__и результат__aenter__()в стек:STACK.extend((__aexit__, __aenter__())
Добавлена в версии 3.5.
Разные инструкции
-
SET_ADD(i) -
Реализует:
item = STACK.pop() set.add(STACK[-i], item)
Используется для реализации множественных генераций.
-
LIST_APPEND(i) -
Реализует:
item = STACK.pop() list.append(STACK[-i], item)
Используется для реализации списочных генераций.
-
MAP_ADD(i) -
Реализует:
value = STACK.pop() key = STACK.pop() dict.__setitem__(STACK[-i], key, value)
Используется для реализации генераций словарей.
Добавлена в версии 3.1.
Изменено в версии 3.8: Значение карты —
STACK[-1], а ключ карты —STACK[-2]. Раньше они были перевёрнуты.
Для всех инструкций SET_ADD, LIST_APPEND и MAP_ADD, в то время как добавляемое значение или пара ключ/значение извлекается, объект контейнера остаётся в стеке, чтобы он был доступен для дальнейших итераций цикла.
-
RETURN_VALUE -
Возвращает
STACK[-1]вызывающей функции.
-
RETURN_CONST(consti) -
Возвращает
co_consts[consti]вызывающей функции.Добавлена в версии 3.12.
-
YIELD_VALUE -
Выдаёт
STACK.pop()из генератора.Изменено в версии 3.11: oparg задаётся как глубина стека.
Изменено в версии 3.12: oparg задаётся как глубина блока исключений для эффективного закрытия генераторов.
-
SETUP_ANNOTATIONS -
Проверяет, определено ли
__annotations__вlocals(), если нет, устанавливается в пустойdict. Эта инструкция генерируется только если тело класса или модуля содержит статические аннотации переменных.Добавлена в версии 3.6.
-
POP_EXCEPT -
Извлекает значение из стека, используемое для восстановления состояния исключения.
Изменено в версии 3.11: Представление исключения в стеке теперь состоит из одного, а не трёх элементов.
-
RERAISE -
Переиздаёт исключение, находящееся в данный момент в верхней части стека. Если oparg отличен от нуля, извлекается дополнительное значение из стека, которое используется для установки
f_lastiтекущего фрейма.Добавлена в версии 3.9.
Изменено в версии 3.11: Представление исключения в стеке теперь состоит из одного, а не трёх элементов.
-
PUSH_EXC_INFO -
Извлекает значение из стека. Помещает текущее исключение в верхнюю часть стека. Возвращает извлечённое значение обратно в стек. Используется в обработчиках исключений.
Добавлена в версии 3.11.
-
CHECK_EXC_MATCH -
Выполняет сопоставление исключений для
except. Проверяет, является лиSTACK[-2]исключением, соответствующимSTACK[-1]. ИзвлекаетSTACK[-1]и помещает в стек логический результат проверки.Добавлена в версии 3.11.
-
CHECK_EG_MATCH -
Выполняет сопоставление исключений для
except*. Применяетsplit(STACK[-1])к группе исключений, представляющейSTACK[-2].В случае совпадения извлекает два элемента из стека и помещает в стек подгруппу, не соответствующую совпадению (
Noneв случае полного совпадения), за которой следует соответствующая подгруппа. При отсутствии совпадения извлекается один элемент (тип соответствия) и помещается в стекNone.Добавлена в версии 3.11.
-
WITH_EXCEPT_START -
Вызывает функцию в позиции 4 в стеке с аргументами (тип, значение, трассировка), представляющими исключение в верхней части стека. Используется для реализации вызова
context_manager.__exit__(*exc_info())при возникновении исключения в оператореwith.Добавлена в версии 3.9.
Изменено в версии 3.11: Функция
__exit__находится в позиции 4 стека, а не в 7. Представление исключения в стеке теперь состоит из одного, а не трёх элементов.
-
LOAD_ASSERTION_ERROR -
Помещает
AssertionErrorв стек. Используется операторомassert.Добавлена в версии 3.9.
-
LOAD_BUILD_CLASS -
Помещает
builtins.__build_class__()в стек. Позже он вызывается для построения класса.
-
BEFORE_WITH -
Эта инструкция выполняет несколько операций перед началом блока with. Во-первых, она загружает
__exit__()из менеджера контекста и помещает его в стек для последующего использования вWITH_EXCEPT_START. Затем вызывается__enter__(). Наконец, результат вызова метода__enter__()помещается в стек.Добавлена в версии 3.11.
-
GET_LEN -
Выполняет
STACK.append(len(STACK[-1])).Добавлена в версии 3.10.
-
MATCH_MAPPING -
Если
STACK[-1]является экземпляромcollections.abc.Mapping(или, технически: если у него установлен флагPy_TPFLAGS_MAPPINGвtp_flags), положитьTrueна стек. В противном случае, положитьFalse.Добавлена в версии 3.10.
-
MATCH_SEQUENCE -
Если
STACK[-1]является экземпляромcollections.abc.Sequenceи не является экземпляромstr/bytes/bytearray(или, технически: если у него установлен флагPy_TPFLAGS_SEQUENCEвtp_flags), положитьTrueна стек. В противном случае, положитьFalse.Добавлена в версии 3.10.
-
MATCH_KEYS -
STACK[-1]— кортеж ключей отображения, аSTACK[-2]— предмет соответствия. ЕслиSTACK[-2]содержит все ключи изSTACK[-1], положить на стек кортежtupleс соответствующими значениями. В противном случае, положитьNone.Добавлена в версии 3.10.
Изменено в версии 3.11: Ранее эта инструкция также помещала на стек логическое значение, указывающее на успех (
True) или неудачу (False).
-
STORE_NAME(namei) -
Реализует
name = STACK.pop(). namei — индекс name в атрибутеco_namesобъекта кода. Компилятор пытается использоватьSTORE_FASTилиSTORE_GLOBAL, если это возможно.
-
UNPACK_SEQUENCE(count) -
Распаковывает
STACK[-1]в count отдельных значений, которые помещаются на стек справа налево. Требуется ровно count значений:assert(len(STACK[-1]) == count) STACK.extend(STACK.pop()[:-count-1:-1])
-
UNPACK_EX(counts) -
Реализует присваивание со звездочным целевым объектом: Распаковывает итерируемый объект в
STACK[-1]в отдельные значения, где общее количество значений может быть меньше количества элементов в итерируемом объекте: одно из новых значений будет списком всех оставшихся элементов.Количество значений до и после значения списка ограничено 255.
Количество значений до значения списка кодируется в аргументе операции. Количество значений после списка, если таковые имеются, кодируется с использованием
EXTENDED_ARG. Вследствие этого, аргумент можно рассматривать как значение в два байта, где младший байт counts — количество значений до значения списка, старший байт counts — количество значений после него.Извлеченные значения помещаются на стек справа налево, т.е.
a, *b, c = dбудет сохранён после выполнения какSTACK.extend((a, b, c)).
-
STORE_ATTR(namei) -
Реализует:
obj = STACK.pop() value = STACK.pop() obj.name = value
-
DELETE_ATTR(namei) -
Реализует:
obj = STACK.pop() del obj.name
-
STORE_GLOBAL(namei) -
Действует как
STORE_NAME, но сохраняет имя как глобальную переменную.
-
DELETE_GLOBAL(namei) -
Действует как
DELETE_NAME, но удаляет глобальное имя.
-
LOAD_CONST(consti) -
Помещает
co_consts[consti]на стек.
-
LOAD_NAME(namei) -
Помещает значение, связанное с
co_names[namei]на стек. Имя ищется в локальных переменных, затем в глобальных, затем в встроенных.
-
LOAD_LOCALS -
Помещает ссылку на словарь локальных переменных на стек. Это используется для подготовки словарей пространства имён для
LOAD_FROM_DICT_OR_DEREFиLOAD_FROM_DICT_OR_GLOBALS.Добавлена в версии 3.12.
-
LOAD_FROM_DICT_OR_GLOBALS(i) -
Извлекает отображение со стека и ищет значение для
co_names[namei]. Если имя не найдено там, ищет его в глобальных, а затем в встроенных, аналогичноLOAD_GLOBAL. Это используется для загрузки глобальных переменных в области анотаций внутри блоков класса.Добавлена в версии 3.12.
-
BUILD_TUPLE(count) -
Создаёт кортеж, потребляя count элементов со стека, и помещает полученный кортеж на стек:
if count == 0: value = () else: STACK = STACK[:-count] value = tuple(STACK[-count:]) STACK.append(value)
-
BUILD_LIST(count) -
Действует как
BUILD_TUPLE, но создаёт список.
-
BUILD_SET(count) -
Действует как
BUILD_TUPLE, но создаёт множество.
-
BUILD_MAP(count) -
Помещает новый объект словаря на стек. Извлекает
2 * countэлементов, чтобы словарь содержал count записей:{..., STACK[-4]: STACK[-3], STACK[-2]: STACK[-1]}.Изменено в версии 3.5: Словарь создаётся из элементов стека, а не пустого словаря, предварительно размеченного для хранения count элементов.
-
BUILD_CONST_KEY_MAP(count) -
Вариант
BUILD_MAP, специализированный для постоянных ключей. Извлекает верхний элемент со стека, содержащий кортеж ключей, затем, начиная сSTACK[-2], извлекает count значений для формирования значений в созданном словаре.Добавлена в версии 3.6.
-
BUILD_STRING(count) -
Конкатенирует count строк со стека и помещает результирующую строку на стек.
Добавлена в версии 3.6.
-
LIST_EXTEND(i) -
Реализует:
seq = STACK.pop() list.extend(STACK[-i], seq)
Используется для построения списков.
Добавлена в версии 3.9.
-
SET_UPDATE(i) -
Реализует:
seq = STACK.pop() set.update(STACK[-i], seq)
Используется для построения множеств.
Добавлена в версии 3.9.
-
DICT_UPDATE(i) -
Реализует:
map = STACK.pop() dict.update(STACK[-i], map)
Используется для построения словарей.
Добавлен в версии 3.9.
-
DICT_MERGE(i) -
Подобно
DICT_UPDATE, но генерирует исключение для дублирующихся ключей.Добавлен в версии 3.9.
-
LOAD_ATTR(namei) -
Если младший бит
nameiне установлен, это заменяетSTACK[-1]наgetattr(STACK[-1], co_names[namei>>1]).Если младший бит
nameiустановлен, это попытается загрузить метод с именемco_names[namei>>1]из объектаSTACK[-1].STACK[-1]извлекается. Этот байткод различает два случая: если уSTACK[-1]есть метод с правильным именем, байткод помещает в стек незавязанный метод иSTACK[-1].STACK[-1]будет использоваться в качестве первого аргумента (self) инструкциейCALLпри вызове незавязанного метода. В противном случае, в стек помещаютсяNULLи объект, возвращённый в результате поиска атрибута.Изменено в версии 3.12: Если младший бит
nameiустановлен, то в стек помещаетсяNULLилиselfсоответственно перед атрибутом или незавязанным методом.
-
LOAD_SUPER_ATTR(namei) -
Эта инструкция реализует
super(), как в нулевом, так и в двух аргументном форматах (например,super().method(),super().attrиsuper(cls, self).method(),super(cls, self).attr).Она извлекает три значения из стека (сверху вниз): -
self: первый аргумент текущего метода -cls: класс, в котором был определён текущий метод - глобальное значениеsuperПо отношению к своему аргументу, она работает аналогично
LOAD_ATTR, за исключением того, чтоnameiсдвигается влево на 2 бита вместо 1.Младший бит
nameiсигнализирует о попытке загрузки метода, как и вLOAD_ATTR, что приводит к помещению в стекNULLи загруженного метода. Когда он не установлен, в стек помещается одно значение.Второй младший бит
namei, если он установлен, означает, что это был вызовsuper()с двумя аргументами (неустановленный означает нулевой аргумент).Добавлен в версии 3.12.
-
COMPARE_OP(opname) -
Выполняет булеву операцию. Название операции можно найти в
cmp_op[opname >> 4].Изменено в версии 3.12: Индекс cmp_op теперь хранится в четырёх старших битах oparg, а не в четырёх младших битах oparg.
-
IS_OP(invert) -
Выполняет сравнение
is, илиis notеслиinvertравно 1.Добавлен в версии 3.9.
-
CONTAINS_OP(invert) -
Выполняет сравнение
in, илиnot inеслиinvertравно 1.Добавлен в версии 3.9.
-
IMPORT_NAME(namei) -
Импортирует модуль
co_names[namei].STACK[-1]иSTACK[-2]извлекаются и предоставляют аргументы fromlist и level для функции__import__(). Объект модуля помещается в стек. Текущее пространство имён не изменяется: для правильного оператора import последующая инструкцияSTORE_FASTизменяет пространство имён.
-
IMPORT_FROM(namei) -
Загружает атрибут
co_names[namei]из модуля, найденного вSTACK[-1]. Результирующий объект помещается в стек, чтобы быть затем сохранён инструкциейSTORE_FAST.
-
JUMP_FORWARD(delta) -
Увеличивает счётчик байткода на delta.
-
JUMP_BACKWARD(delta) -
Уменьшает счётчик байткода на delta. Проверяет наличие прерываний.
Добавлен в версии 3.11.
-
JUMP_BACKWARD_NO_INTERRUPT(delta) -
Уменьшает счётчик байткода на delta. Не проверяет наличие прерываний.
Добавлен в версии 3.11.
-
POP_JUMP_IF_TRUE(delta) -
Если
STACK[-1]истинно, увеличивает счётчик байткода на delta.STACK[-1]извлекается.Изменено в версии 3.11: opar является относительным смещением, а не абсолютной меткой. Эта инструкция — псевдоинструкция, заменённая в итоговом байткоде направленными версиями (вперёд/назад).
Изменено в версии 3.12: Это больше не псевдоинструкция.
-
POP_JUMP_IF_FALSE(delta) -
Если
STACK[-1]ложно, увеличивает счётчик байткода на delta.STACK[-1]извлекается.Изменено в версии 3.11: opar является относительным смещением, а не абсолютной меткой. Эта инструкция — псевдоинструкция, заменённая в итоговом байткоде направленными версиями (вперёд/назад).
Изменено в версии 3.12: Это больше не псевдоинструкция.
-
POP_JUMP_IF_NOT_NONE(delta) -
Если
STACK[-1]не равноNone, увеличивает счётчик байткода на delta.STACK[-1]извлекается.Эта инструкция — псевдоинструкция, заменённая в итоговом байткоде направленными версиями (вперёд/назад).
Добавлен в версии 3.11.
Изменено в версии 3.12: Это больше не псевдоинструкция.
-
POP_JUMP_IF_NONE(delta) -
Если
STACK[-1]равноNone, увеличивает счётчик байткода на delta.STACK[-1]извлекается.Эта инструкция — псевдоинструкция, заменённая в итоговом байткоде направленными версиями (вперёд/назад).
Добавлен в версии 3.11.
Изменено в версии 3.12: Это больше не псевдоинструкция.
-
FOR_ITER(delta) -
STACK[-1]— итератор. Вызывается его метод__next__(). Если это возвращает новое значение, помещает его в стек (оставляя итератор ниже). Если итератор указывает, что он исчерпан, счётчик байткода увеличивается на delta.Изменено в версии 3.12: До версии 3.11 итератор извлекался, когда он был исчерпан.
-
LOAD_GLOBAL(namei) -
Загружает глобальную переменную с именем
co_names[namei>>1]в стек.Изменено в версии 3.11: Если младший бит
nameiустановлен, то в стек помещаетсяNULLперед глобальной переменной.
-
LOAD_FAST(var_num) -
Помещает ссылку на локальную переменную
co_varnames[var_num]в стек.Изменено в версии 3.12: Эта инструкция используется только в ситуациях, когда локальная переменная гарантированно инициализирована. Она не может вызвать
UnboundLocalError.
-
LOAD_FAST_CHECK(var_num) -
Помещает ссылку на локальную переменную
co_varnames[var_num]в стек, вызывая исключениеUnboundLocalError, если локальная переменная не была инициализирована.Добавлен в версии 3.12.
-
LOAD_FAST_AND_CLEAR(var_num) -
Помещает ссылку на локальную
co_varnames[var_num]в стек (или помещаетNULLв стек, если локальная переменная не была инициализирована) и устанавливаетco_varnames[var_num]вNULL.Добавлена в версии 3.12.
-
STORE_FAST(var_num) -
Сохраняет
STACK.pop()в локальнуюco_varnames[var_num].
-
DELETE_FAST(var_num) -
Удаляет локальную
co_varnames[var_num].
-
MAKE_CELL(i) -
Создаёт новую ячейку в слоте
i. Если этот слот не пуст, то его значение сохраняется в новую ячейку.Добавлена в версии 3.11.
-
LOAD_CLOSURE(i) -
Помещает ссылку на ячейку, содержащуюся в слоте
iхранилища «быстрых локальных переменных». Имя переменной —co_fastlocalnames[i].Обратите внимание, что
LOAD_CLOSUREфактически является псевдонимом дляLOAD_FAST. Он существует для повышения читабельности байткода.Изменено в версии 3.11:
iбольше не смещён относительно длиныco_varnames.
-
LOAD_DEREF(i) -
Загружает ячейку, содержащуюся в слоте
iхранилища «быстрых локальных переменных». Помещает ссылку на объект, содержащийся в ячейке, в стек.Изменено в версии 3.11:
iбольше не смещён относительно длиныco_varnames.
-
LOAD_FROM_DICT_OR_DEREF(i) -
Извлекает отображение из стека и ищет имя, связанное со слотом
iхранилища «быстрых локальных переменных» в этом отображении. Если имя не найдено, загружает его из ячейки, содержащейся в слотеi, аналогичноLOAD_DEREF. Это используется для загрузки свободных переменных в телах классов (ранее для этого использовалосьLOAD_CLASSDEREF) и в областях аннотаций внутри тел классов.Добавлена в версии 3.12.
-
STORE_DEREF(i) -
Сохраняет
STACK.pop()в ячейку, содержащуюся в слотеiхранилища «быстрых локальных переменных».Изменено в версии 3.11:
iбольше не смещён относительно длиныco_varnames.
-
DELETE_DEREF(i) -
Очищает ячейку, содержащуюся в слоте
iхранилища «быстрых локальных переменных». Используется операторомdel.Добавлена в версии 3.2.
Изменено в версии 3.11:
iбольше не смещён относительно длиныco_varnames.
-
COPY_FREE_VARS(n) -
Копирует
nсвободные переменные из замыкания в кадр. Устраняет необходимость в специальном коде со стороны вызывающего кода при вызове замыканий.Добавлена в версии 3.11.
-
RAISE_VARARGS(argc) -
Выбрасывает исключение, используя одну из 3 форм оператора
raise, в зависимости от значения argc:- 0:
raise(перевыброс предыдущего исключения) - 1:
raise STACK[-1](выбрасывает экземпляр или тип исключения вSTACK[-1]) - 2:
raise STACK[-2] from STACK[-1](выбрасывает экземпляр или тип исключения вSTACK[-2]с__cause__, установленным вSTACK[-1])
- 0:
-
CALL(argc) -
Вызывает вызываемый объект с количеством аргументов, указанным
argc, включая именованные аргументы, указанные предшествующимKW_NAMES, если таковые имеются. В стеке находятся (в порядке возрастания):- NULL
- Вызываемый объект
- Позиционные аргументы
- Именованные аргументы
или:
- Вызываемый объект
self- Остальные позиционные аргументы
- Именованные аргументы
argc— общее количество позиционных и именованных аргументов, исключаяselfв случае отсутствияNULL.CALLизвлекает все аргументы и вызываемый объект из стека, вызывает вызываемый объект с этими аргументами и помещает возвращённое значение вызываемого объекта в стек.Добавлена в версии 3.11.
-
CALL_FUNCTION_EX(flags) -
Вызывает вызываемый объект с переменным набором позиционных и именованных аргументов. Если младший бит flags установлен, верхняя часть стека содержит объект отображения, содержащий дополнительные именованные аргументы. Перед вызовом вызываемого объекта объект отображения и объект-итерируемый «распаковываются», и их содержимое передаётся как именованные и позиционные аргументы соответственно.
CALL_FUNCTION_EXизвлекает все аргументы и вызываемый объект из стека, вызывает вызываемый объект с этими аргументами и помещает возвращённое значение вызываемого объекта в стек.Добавлена в версии 3.6.
-
PUSH_NULL -
Помещает
NULLв стек. Используется в последовательности вызова для соответствияNULL, помещаемомуLOAD_METHODдля вызовов, не являющихся методами.Добавлена в версии 3.11.
-
KW_NAMES(consti) -
Префикс для
CALL. Сохраняет ссылку наco_consts[consti]во внутреннюю переменную для использования вCALL.co_consts[consti]должен быть кортежем строк.Добавлена в версии 3.11.
-
MAKE_FUNCTION(flags) -
Помещает новый объект функции в стек. Снизу вверх, потребляемый стек должен состоять из значений, если аргумент несёт указанное значение флага:
-
0x01кортеж значений по умолчанию для позиционных-только и позиционных-или-именованных параметров в порядке следования -
0x02словарь значений по умолчанию для именованных-только параметров -
0x04кортеж строк, содержащий аннотации параметров -
0x08кортеж, содержащий ячейки для свободных переменных, создавая замыкание - код, связанный с функцией (в
STACK[-1])
Изменено в версии 3.10: Значение флага
0x04является кортежем строк вместо словаряИзменено в версии 3.11: Квалифицированное имя в
STACK[-1]было удалено. -
-
BUILD_SLICE(argc) -
Помещает объект среза в стек. argc должен быть равен 2 или 3. Если он равен 2, реализует:
end = STACK.pop() start = STACK.pop() STACK.append(slice(start, end))
Если он равен 3, реализует:
step = STACK.pop() end = STACK.pop() start = STACK.pop() STACK.append(slice(start, end, step))
См. встроенную функцию
slice()для получения дополнительной информации.
-
EXTENDED_ARG(ext) -
Префикс для любого оператора, имеющего слишком большой аргумент, чтобы поместиться в стандартный один байт. ext содержит дополнительный байт, который действует как старшие биты в аргументе. Для каждого оператора разрешено не более трёх префиксных
EXTENDED_ARG, образующих аргумент от двухбайтового до четырёхбайтового.
-
FORMAT_VALUE(flags) -
Используется для реализации форматированных строковых литералов (f-строк). Извлекает необязательный fmt_spec со стека, а затем обязательный value. flags интерпретируется следующим образом:
-
(flags & 0x03) == 0x00: value форматируется как есть. -
(flags & 0x03) == 0x01: вызываетсяstr()для value перед его форматированием. -
(flags & 0x03) == 0x02: вызываетсяrepr()для value перед его форматированием. -
(flags & 0x03) == 0x03: вызываетсяascii()для value перед его форматированием. -
(flags & 0x04) == 0x04: извлекает fmt_spec со стека и использует его, иначе использует пустой fmt_spec.
Форматирование выполняется с помощью
PyObject_Format(). Результат помещается на стек.Добавлен в версии 3.6.
-
-
MATCH_CLASS(count) -
STACK[-1]— кортеж имён атрибутов-ключей,STACK[-2]— класс, с которым производится сопоставление, иSTACK[-3]— объект-субъект сопоставления. count — количество позиционных подшаблонов.Извлекаются
STACK[-1],STACK[-2], иSTACK[-3]. ЕслиSTACK[-3]является экземпляромSTACK[-2]и имеет необходимые позиционные и ключевые атрибуты, соответствующие count иSTACK[-1], на стек помещается кортеж извлечённых атрибутов. В противном случае, помещаетсяNone.Добавлен в версии 3.10.
Изменено в версии 3.11: Ранее эта инструкция также помещала на стек булевое значение, указывающее на успех (
True) или неудачу (False).
-
RESUME(where) -
Пустая операция. Выполняет внутреннее отслеживание, отладку и проверки оптимизации.
Операнд
whereотмечает место, где происходитRESUME:-
0Начало функции, которая не является генератором, корутиной или асинхронным генератором -
1После выраженияyield -
2После выраженияyield from -
3После выраженияawait
Добавлен в версии 3.11.
-
-
RETURN_GENERATOR -
Создаёт генератор, корутину или асинхронный генератор из текущей фреймворка. Используется в качестве первой инструкции в коде объекта для вышеупомянутых вызовов. Очищает текущую фреймворку и возвращает созданный генератор.
Добавлен в версии 3.11.
-
SEND(delta) -
Эквивалентно
STACK[-1] = STACK[-2].send(STACK[-1]). Используется в операторахyield fromиawait.Если вызов вызывает
StopIteration, извлекается верхнее значение со стека, на стек помещается атрибутvalueисключения, и счётчик байткода увеличивается на delta.Добавлен в версии 3.11.
-
HAVE_ARGUMENT -
Это не совсем инструкция. Она определяет границу между инструкциями в диапазоне [0,255], которые не используют свой аргумент, и теми, которые используют (
< HAVE_ARGUMENTи>= HAVE_ARGUMENT, соответственно).Если ваше приложение использует псевдоинструкции, используйте коллекцию
hasargвместо этого.Изменено в версии 3.6: Теперь у каждой инструкции есть аргумент, но инструкции
< HAVE_ARGUMENTигнорируют его. Раньше аргументы имели только инструкции>= HAVE_ARGUMENT.Изменено в версии 3.12: В модуль
disбыли добавлены псевдоинструкции, и для них неверно, что сравнение сHAVE_ARGUMENTуказывает, используют ли они свой аргумент.
-
CALL_INTRINSIC_1 -
Вызывает функцию-интринсик с одним аргументом. Передаёт
STACK[-1]в качестве аргумента и устанавливаетSTACK[-1]в результат. Используется для реализации функциональности, которая не является критически важной для производительности.Операнд определяет, какая функция-интринсик вызывается:
Операнд
Описание
INTRINSIC_1_INVALIDНедействительно
INTRINSIC_PRINTВыводит аргумент в стандартный вывод. Используется в REPL.
INTRINSIC_IMPORT_STARВыполняет
import *для указанного модуля.INTRINSIC_STOPITERATION_ERRORИзвлекает возвращаемое значение из исключения
StopIteration.INTRINSIC_ASYNC_GEN_WRAPОборачивает значение асинхронного генератора
INTRINSIC_UNARY_POSITIVEВыполняет унарную операцию
+INTRINSIC_LIST_TO_TUPLEПреобразует список в кортеж
INTRINSIC_TYPEVARСоздаёт
typing.TypeVarINTRINSIC_PARAMSPECСоздаёт
typing.ParamSpecINTRINSIC_TYPEVARTUPLEСоздаёт
typing.TypeVarTupleINTRINSIC_SUBSCRIPT_GENERICВозвращает
typing.Generic, индексированный аргументомINTRINSIC_TYPEALIASСоздаёт
typing.TypeAliasType; используется в оператореtype. Аргумент — кортеж из имени псевдонима типа, параметров типа и значения.Добавлен в версии 3.12.
-
CALL_INTRINSIC_2 -
Вызывает функцию-интринсик с двумя аргументами. Используется для реализации функциональности, которая не является критически важной для производительности:
arg2 = STACK.pop() arg1 = STACK.pop() result = intrinsic2(arg1, arg2) STACK.push(result)
Операнд определяет, какая функция-интринсик вызывается:
Операнд
Описание
INTRINSIC_2_INVALIDНедействительно
INTRINSIC_PREP_RERAISE_STARВычисляет
ExceptionGroupдля повышения изtry-except*.INTRINSIC_TYPEVAR_WITH_BOUNDСоздаёт
typing.TypeVarс ограничением.INTRINSIC_TYPEVAR_WITH_CONSTRAINTSСоздаёт
typing.TypeVarс ограничениями.INTRINSIC_SET_FUNCTION_TYPE_PARAMSУстанавливает атрибут
__type_params__функции.Добавлен в версии 3.12.
Псевдоинструкции
Эти инструкции не появляются в байткоде Python. Они используются компилятором, но заменяются реальными инструкциями или удаляются перед генерацией байткода.
-
SETUP_FINALLY(target) -
Устанавливает обработчик исключений для следующего блока кода. Если произойдёт исключение, уровень стека значений восстанавливается до текущего состояния, и управление передаётся обработчику исключений по адресу
target.
-
SETUP_CLEANUP(target) -
Подобно
SETUP_FINALLY, но в случае исключения также помещает последнюю инструкцию (lasti) на стек, чтобыRERAISEмогла её восстановить. Если произойдёт исключение, уровень стека значений и последняя инструкция в фреймворке восстанавливаются до текущего состояния, и управление передаётся обработчику исключений по адресуtarget.
-
SETUP_WITH(target) -
Подобно
SETUP_CLEANUP, но в случае исключения извлекается ещё один элемент со стека перед передачей управления обработчику исключений по адресуtarget.Этот вариант используется в конструкциях
withиasync with, которые помещают возвращаемое значение метода__enter__()или__aenter__()контекстного менеджера на стек.
-
POP_BLOCK -
Помечает конец блока кода, связанного с последним
SETUP_FINALLY,SETUP_CLEANUPилиSETUP_WITH.
-
JUMP
-
JUMP_NO_INTERRUPT -
Инструкции условного перехода, которые заменяются на соответствующие (прямые/обратные) инструкции ассемблером.
-
LOAD_METHOD -
Оптимизированный поиск несвязанного метода. Выводится как инструкция
LOAD_ATTRс флагом, установленным в аргументе.
Сборки инструкций
Эти сборки предназначены для автоматической интроспекции инструкций байткода:
Изменено в версии 3.12: Теперь сборки содержат и псевдоинструкции, и инструментированные инструкции. Это инструкции с кодами >= MIN_PSEUDO_OPCODE и >= MIN_INSTRUMENTED_OPCODE.
-
dis.opname -
Последовательность имен операций, индексируемая с использованием байткода.
-
dis.opmap -
Словарь, сопоставляющий имена операций с байткодами.
-
dis.cmp_op -
Последовательность всех имен операций сравнения.
-
dis.hasarg -
Последовательность байткодов, использующих свой аргумент.
Добавлена в версии 3.12.
-
dis.hasconst -
Последовательность байткодов, которые обращаются к константе.
-
dis.hasfree -
Последовательность байткодов, которые обращаются к свободной переменной. «Свободные» в данном контексте относятся к именам в текущей области видимости, к которым обращаются внутренние области видимости, или именам во внешних областях видимости, к которым обращаются из этой области видимости. Это не включает ссылки на глобальные или встроенные области видимости.
-
dis.hasname -
Последовательность байткодов, которые обращаются к атрибуту по имени.
-
dis.hasjrel -
Последовательность байткодов, которые имеют относительную цель перехода.
-
dis.hasjabs -
Последовательность байткодов, которые имеют абсолютную цель перехода.
-
dis.haslocal -
Последовательность байткодов, которые обращаются к локальной переменной.
-
dis.hascompare -
Последовательность байткодов операций булевой логики.
-
dis.hasexc -
Последовательность байткодов, которые устанавливают обработчик исключений.
Добавлена в версии 3.12.
© 2001–2024 Python Software Foundation
Licensed under the PSF License.
https://docs.python.org/3.12/library/dis.html