8000 gh-105481: add OPCODE_IS_INSTRUMENTED (generated from bytecodes.c) to replace MIN_INSTRUMENTED_OPCODE (defined in opcode.py) by iritkatriel · Pull Request #107276 · python/cpython · GitHub
[go: up one dir, main page]

Skip to content

gh-105481: add OPCODE_IS_INSTRUMENTED (generated from bytecodes.c) to replace MIN_INSTRUMENTED_OPCODE (defined in opcode.py) #107276

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
wants to merge 4 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions Include/cpython/compile.h
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,7 @@ PyAPI_FUNC(int) PyUnstable_OpcodeHasJump(int opcode);
PyAPI_FUNC(int) PyUnstable_OpcodeHasFree(int opcode);
PyAPI_FUNC(int) PyUnstable_OpcodeHasLocal(int opcode);
PyAPI_FUNC(int) PyUnstable_OpcodeHasExc(int opcode);
PyAPI_FUNC(int) PyUnstable_OpcodeIsInstrumented(int opcode);

PyAPI_FUNC(PyObject*) _PyUnstable_GetUnaryIntrinsicName(int index);
PyAPI_FUNC(PyObject*) _PyUnstable_GetBinaryIntrinsicName(int index);
39 changes: 21 additions & 18 deletions Include/internal/pycore_opcode_metadata.h
Original file line number Diff line number Diff line change
Expand Up @@ -949,20 +949,23 @@ enum InstructionFormat { INSTR_FMT_IB, INSTR_FMT_IBC, INSTR_FMT_IBC00, INSTR_FMT

#define IS_VALID_OPCODE(OP) \
(((OP) >= 0) && ((OP) < OPCODE_METADATA_SIZE) && \
(_PyOpcode_opcode_metadata[(OP)].valid_entry))
(_PyOpcode_opcode_metadata[(OP)].valid_entry)) || \
((OP) == INSTRUMENTED_LINE)

#define HAS_ARG_FLAG (1)
#define HAS_CONST_FLAG (2)
#define HAS_NAME_FLAG (4)
#define HAS_JUMP_FLAG (8)
#define HAS_FREE_FLAG (16)
#define HAS_LOCAL_FLAG (32)
#define IS_INSTRUMENTED_FLAG (64)
#define OPCODE_HAS_ARG(OP) (_PyOpcode_opcode_metadata[OP].flags & (HAS_ARG_FLAG))
#define OPCODE_HAS_CONST(OP) (_PyOpcode_opcode_metadata[OP].flags & (HAS_CONST_FLAG))
#define OPCODE_HAS_NAME(OP) (_PyOpcode_opcode_metadata[OP].flags & (HAS_NAME_FLAG))
#define OPCODE_HAS_JUMP(OP) (_PyOpcode_opcode_metadata[OP].flags & (HAS_JUMP_FLAG))
#define OPCODE_HAS_FREE(OP) (_PyOpcode_opcode_metadata[OP].flags & (HAS_FREE_FLAG))
#define OPCODE_HAS_LOCAL(OP) (_PyOpcode_opcode_metadata[OP].flags & (HAS_LOCAL_FLAG))
#define OPCODE_IS_INSTRUMENTED(OP) (_PyOpcode_opcode_metadata[OP].flags & (IS_INSTRUMENTED_FLAG)) || ((OP) == INSTRUMENTED_LINE)

struct opcode_metadata {
bool valid_entry;
Expand Down Expand Up @@ -998,7 +1001,7 @@ extern const char * const _PyOpcode_uop_name[OPCODE_UOP_NAME_SIZE];
const struct opcode_metadata _PyOpcode_opcode_metadata[OPCODE_METADATA_SIZE] = {
[NOP] = { true, INSTR_FMT_IX, 0 },
[RESUME] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_RESUME] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_RESUME] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | IS_INSTRUMENTED_FLAG },
[LOAD_CLOSURE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | HAS_LOCAL_FLAG },
[LOAD_FAST_CHECK] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | HAS_LOCAL_FLAG },
[LOAD_FAST] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | HAS_LOCAL_FLAG },
Expand All @@ -1012,9 +1015,9 @@ const struct opcode_metadata _PyOpcode_opcode_metadata[OPCODE_METADATA_SIZE] = {
[POP_TOP] = { true, INSTR_FMT_IX, 0 },
[PUSH_NULL] = { true, INSTR_FMT_IX, 0 },
[ 8000 END_FOR] = { true, INSTR_FMT_IB, 0 },
[INSTRUMENTED_END_FOR] = { true, INSTR_FMT_IX, 0 },
[INSTRUMENTED_END_FOR] = { true, INSTR_FMT_IX, IS_INSTRUMENTED_FLAG },
[END_SEND] = { true, INSTR_FMT_IX, 0 },
[INSTRUMENTED_END_SEND] = { true, INSTR_FMT_IX, 0 },
[INSTRUMENTED_END_SEND] = { true, INSTR_FMT_IX, IS_INSTRUMENTED_FLAG },
[UNARY_NEGATIVE] = { true, INSTR_FMT_IX, 0 },
[UNARY_NOT] = { true, INSTR_FMT_IX, 0 },
[TO_BOOL] = { true, INSTR_FMT_IXC00, 0 },
Expand Down Expand Up @@ -1051,15 +1054,15 @@ const struct opcode_metadata _PyOpcode_opcode_metadata[OPCODE_METADATA_SIZE] = {
[RAISE_VARARGS] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INTERPRETER_EXIT] = { true, INSTR_FMT_IX, 0 },
[RETURN_VALUE] = { true, INSTR_FMT_IX, 0 },
[INSTRUMENTED_RETURN_VALUE] = { true, INSTR_FMT_IX, 0 },
[INSTRUMENTED_RETURN_VALUE] = { true, INSTR_FMT_IX, IS_INSTRUMENTED_FLAG },
[RETURN_CONST] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | HAS_CONST_FLAG },
[INSTRUMENTED_RETURN_CONST] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | HAS_CONST_FLAG },
[INSTRUMENTED_RETURN_CONST] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | HAS_CONST_FLAG | IS_INSTRUMENTED_FLAG },
[GET_AITER] = { true, INSTR_FMT_IX, 0 },
[GET_ANEXT] = { true, INSTR_FMT_IX, 0 },
[GET_AWAITABLE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[SEND] = { true, INSTR_FMT_IBC, HAS_ARG_FLAG | HAS_JUMP_FLAG },
[SEND_GEN] = { true, INSTR_FMT_IBC, HAS_ARG_FLAG },
[INSTRUMENTED_YIELD_VALUE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_YIELD_VALUE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | IS_INSTRUMENTED_FLAG },
[YIELD_VALUE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[POP_EXCEPT] = { true, INSTR_FMT_IX, 0 },
[RERAISE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
Expand Down Expand Up @@ -1103,7 +1106,7 @@ const struct opcode_metadata _PyOpcode_opcode_metadata[OPCODE_METADATA_SIZE] = {
[DICT_UPDATE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[DICT_MERGE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[MAP_ADD] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_LOAD_SUPER_ATTR] = { true, INSTR_FMT_IBC00000000, HAS_ARG_FLAG },
[INSTRUMENTED_LOAD_SUPER_ATTR] = { true, INSTR_FMT_IBC00000000, HAS_ARG_FLAG | IS_INSTRUMENTED_FLAG },
[LOAD_SUPER_ATTR] = { true, INSTR_FMT_IBC, HAS_ARG_FLAG | HAS_NAME_FLAG },
[LOAD_SUPER_METHOD] = { true, INSTR_FMT_IBC, HAS_ARG_FLAG | HAS_NAME_FLAG },
[LOAD_ZERO_SUPER_METHOD] = { true, INSTR_FMT_IBC, HAS_ARG_FLAG | HAS_NAME_FLAG },
Expand Down Expand Up @@ -1150,7 +1153,7 @@ const struct opcode_metadata _PyOpcode_opcode_metadata[OPCODE_METADATA_SIZE] = {
[GET_ITER] = { true, INSTR_FMT_IX, 0 },
[GET_YIELD_FROM_ITER] = { true, INSTR_FMT_IX, 0 },
[FOR_ITER] = { true, INSTR_FMT_IBC, HAS_ARG_FLAG | HAS_JUMP_FLAG },
[INSTRUMENTED_FOR_ITER] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_FOR_ITER] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | IS_INSTRUMENTED_FLAG },
[FOR_ITER_LIST] = { true, INSTR_FMT_IBC, HAS_ARG_FLAG | HAS_JUMP_FLAG },
[FOR_ITER_TUPLE] = { true, INSTR_FMT_IBC, HAS_ARG_FLAG | HAS_JUMP_FLAG },
[FOR_ITER_RANGE] = { true, INSTR_FMT_IBC, HAS_ARG_FLAG | HAS_JUMP_FLAG },
Expand All @@ -1169,7 +1172,7 @@ const struct opcode_metadata _PyOpcode_opcode_metadata[OPCODE_METADATA_SIZE] = {
[LOAD_ATTR_NONDESCRIPTOR_NO_DICT] = { true, INSTR_FMT_IBC00000000, HAS_ARG_FLAG },
[LOAD_ATTR_METHOD_LAZY_DICT] = { true, INSTR_FMT_IBC00000000, HAS_ARG_FLAG },
[KW_NAMES] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | HAS_CONST_FLAG },
[INSTRUMENTED_CALL] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_CALL] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | IS_INSTRUMENTED_FLAG },
[CALL] = { true, INSTR_FMT_IBC00, HAS_ARG_FLAG },
[CALL_BOUND_METHOD_EXACT_ARGS] = { true, INSTR_FMT_IBC00, HAS_ARG_FLAG },
[CALL_PY_EXACT_ARGS] = { true, INSTR_FMT_IBC00, HAS_ARG_FLAG },
Expand All @@ -1190,7 +1193,7 @@ const struct opcode_metadata _PyOpcode_opcode_metadata[OPCODE_METADATA_SIZE] = {
[CALL_METHOD_DESCRIPTOR_FAST_WITH_KEYWORDS] = { true, INSTR_FMT_IBC00, HAS_ARG_FLAG },
[CALL_NO_KW_METHOD_DESCRIPTOR_NOARGS] = { true, INSTR_FMT_IBC00, HAS_ARG_FLAG },
[CALL_NO_KW_METHOD_DESCRIPTOR_FAST] = { true, INSTR_FMT_IBC00, HAS_ARG_FLAG },
[INSTRUMENTED_CALL_FUNCTION_EX] = { true, INSTR_FMT_IX, 0 },
[INSTRUMENTED_CALL_FUNCTION_EX] = { true, INSTR_FMT_IX, IS_INSTRUMENTED_FLAG },
[CALL_FUNCTION_EX] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[MAKE_FUNCTION] = { true, INSTR_FMT_IX, 0 },
[SET_FUNCTION_ATTRIBUTE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
Expand All @@ -1202,13 +1205,13 @@ const struct opcode_metadata _PyOpcode_opcode_metadata[OPCODE_METADATA_SIZE] = {
[COPY] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[BINARY_OP] = { true, INSTR_FMT_IBC, HAS_ARG_FLAG },
[SWAP] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_INSTRUCTION] = { true, INSTR_FMT_IX, 0 },
[INSTRUMENTED_JUMP_FORWARD] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_JUMP_BACKWARD] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_POP_JUMP_IF_TRUE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_POP_JUMP_IF_FALSE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_POP_JUMP_IF_NONE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_POP_JUMP_IF_NOT_NONE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[INSTRUMENTED_INSTRUCTION] = { true, INSTR_FMT_IX, IS_INSTRUMENTED_FLAG },
[INSTRUMENTED_JUMP_FORWARD] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | IS_INSTRUMENTED_FLAG },
[INSTRUMENTED_JUMP_BACKWARD] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | IS_INSTRUMENTED_FLAG },
[INSTRUMENTED_POP_JUMP_IF_TRUE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | IS_INSTRUMENTED_FLAG },
[INSTRUMENTED_POP_JUMP_IF_FALSE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | IS_INSTRUMENTED_FLAG },
[INSTRUMENTED_POP_JUMP_IF_NONE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | IS_INSTRUMENTED_FLAG },
[INSTRUMENTED_POP_JUMP_IF_NOT_NONE] = { true, INSTR_FMT_IB, HAS_ARG_FLAG | IS_INSTRUMENTED_FLAG },
[EXTENDED_ARG] = { true, INSTR_FMT_IB, HAS_ARG_FLAG },
[CACHE] = { true, INSTR_FMT_IX, 0 },
[RESERVED] = { true, INSTR_FMT_IX, 0 },
Expand Down
1 change: 0 additions & 1 deletion Include/opcode.h

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 0 additions & 1 deletion Lib/opcode.py
Original file line number Diff line number Diff line change
Expand Up @@ -192,7 +192,6 @@ def pseudo_op(name, op, real_ops):
def_op('ENTER_EXECUTOR', 230)

# Instrumented instructions
MIN_INSTRUMENTED_OPCODE = 237

def_op('INSTRUMENTED_LOAD_SUPER_ATTR', 237)
def_op('INSTRUMENTED_POP_JUMP_IF_NONE', 238)
Expand Down
5 changes: 3 additions & 2 deletions Lib/test/test__opcode.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ def test_invalid_opcodes(self):
self.check_bool_function_result(_opcode.has_free, invalid, False)
self.check_bool_function_result(_opcode.has_local, invalid, False)
self.check_bool_function_result(_opcode.has_exc, invalid, False)
self.check_bool_function_result(_opcode.is_instrumented, invalid, False)

def test_is_valid(self):
names = [
Expand Down Expand Up @@ -57,7 +58,7 @@ def test_stack_effect(self):
# All defined opcodes
has_arg = dis.hasarg
for name, code in filter(lambda item: item[0] not in dis.deoptmap, dis.opmap.items()):
if code >= opcode.MIN_INSTRUMENTED_OPCODE:
if _opcode.is_instrumented(code):
continue
with self.subTest(opname=name):
stack_effect(code)
Expand All @@ -82,7 +83,7 @@ def test_stack_effect_jump(self):
has_exc = dis.hasexc
has_jump = dis.hasjabs + dis.hasjrel
for name, code in filter(lambda item: item[0] not in dis.deoptmap, dis.opmap.items()):
if code >= opcode.MIN_INSTRUMENTED_OPCODE:
if _opcode.is_instrumented(code):
continue
with self.subTest(opname=name):
if code not in has_arg:
Expand Down
19 changes: 19 additions & 0 deletions Modules/_opcode.c
Original file line number Diff line number Diff line change
Expand Up @@ -203,6 +203,24 @@ _opcode_has_exc_impl(PyObject *module, int opcode)
PyUnstable_OpcodeHasExc(opcode);
}

/*[clinic input]

_opcode.is_instrumented -> bool

opcode: int

Return True if the opcode is instrumented, False otherwise.
[clinic start generated code]*/

static int
_opcode_is_instrumented_impl(PyObject *module, int opcode)
/*[clinic end generated code: output=dbfb4dce2bef87c8 input=f4bcce48607a9266]*/
{
return PyUnstable_OpcodeIsValid(opcode) && F438 ;
PyUnstable_OpcodeIsInstrumented(opcode);
}


/*[clinic input]

_opcode.get_specialization_stats
Expand Down Expand Up @@ -286,6 +304,7 @@ opcode_functions[] = {
_OPCODE_HAS_FREE_METHODDEF
_OPCODE_HAS_LOCAL_METHODDEF
_OPCODE_HAS_EXC_METHODDEF
_OPCODE_IS_INSTRUMENTED_METHODDEF
_OPCODE_GET_SPECIALIZATION_STATS_METHODDEF
_OPCODE_GET_INTRINSIC1_DESCS_METHODDEF
_OPCODE_GET_INTRINSIC2_DESCS_METHODDEF
Expand Down
65 changes: 64 additions & 1 deletion Modules/clinic/_opcode.c.h

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

6 changes: 6 additions & 0 deletions Python/compile.c
Original file line number Diff line number Diff line change
Expand Up @@ -915,6 +915,12 @@ PyUnstable_OpcodeHasExc(int opcode)
return IS_BLOCK_PUSH_OPCODE(opcode);
}

int
PyUnstable_OpcodeIsInstrumented(int opcode)
{
return OPCODE_IS_INSTRUMENTED(opcode);
}

static int
codegen_addop_noarg(instr_sequence *seq, int opcode, location loc)
{
Expand Down
7 changes: 4 additions & 3 deletions Python/instrumentation.c
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,13 @@
#include "pycore_frame.h"
#include "pycore_interp.h"
#include "pycore_long.h"
#include "pycore_modsupport.h" // _PyModule_CreateInitialized()
#include "pycore_modsupport.h" // _PyModule_CreateInitialized()
#include "pycore_namespace.h"
#include "pycore_object.h"
#include "pycore_opcode.h"
#include "pycore_opcode_metadata.h" // OPCODE_IS_INSTRUMENTED
#include "pycore_pyerrors.h"
#include "pycore_pystate.h" // _PyInterpreterState_GET()
#include "pycore_pystate.h" // _PyInterpreterState_GET()

/* Uncomment this to dump debugging output when assertions fail */
// #define INSTRUMENT_DEBUG 1
Expand Down Expand Up @@ -130,7 +131,7 @@ is_instrumented(int opcode)
{
assert(opcode != 0);
assert(opcode != RESERVED);
return opcode >= MIN_INSTRUMENTED_OPCODE;
return OPCODE_IS_INSTRUMENTED(opcode);
}

#ifndef NDEBUG
Expand Down
7 changes: 4 additions & 3 deletions Python/specialize.c
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,9 @@
#include "pycore_long.h"
#include "pycore_moduleobject.h"
#include "pycore_object.h"
#include "pycore_opcode.h" // _PyOpcode_Caches
#include "pycore_pylifecycle.h" // _PyOS_URandomNonblock()
#include "pycore_opcode.h" // _PyOpcode_Caches
#include "pycore_opcode_metadata.h" // OPCODE_IS_INSTRUMENTED
#include "pycore_pylifecycle.h" // _PyOS_URandomNonblock()


#include <stdlib.h> // rand()
Expand Down Expand Up @@ -279,7 +280,7 @@ _PyCode_Quicken(PyCodeObject *code)
_Py_CODEUNIT *instructions = _PyCode_CODE(code);
for (int i = 0; i < Py_SIZE(code); i++) {
opcode = _Py_GetBaseOpcode(code, i);
assert(opcode < MIN_INSTRUMENTED_OPCODE);
assert(!OPCODE_IS_INSTRUMENTED(opcode));
int caches = _PyOpcode_Caches[opcode];
if (caches) {
instructions[i + 1].cache = adaptive_counter_warmup();
Expand Down
3 changes: 0 additions & 3 deletions Tools/build/generate_opcode_h.py
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,6 @@ def main(opcode_py,
ENABLE_SPECIALIZATION = opcode["ENABLE_SPECIALIZATION"]
MIN_PSEUDO_OPCODE = opcode["MIN_PSEUDO_OPCODE"]
MAX_PSEUDO_OPCODE = opcode["MAX_PSEUDO_OPCODE"]
MIN_INSTRUMENTED_OPCODE = opcode["MIN_INSTRUMENTED_OPCODE"]

NUM_OPCODES = len(opname)
used = [ False ] * len(opname)
Expand All @@ -103,8 +102,6 @@ def main(opcode_py,
op = opmap[name]
if op == MIN_PSEUDO_OPCODE:
fobj.write(DEFINE.format("MIN_PSEUDO_OPCODE", MIN_PSEUDO_OPCODE))
if op == MIN_INSTRUMENTED_OPCODE:
fobj.write(DEFINE.format("MIN_INSTRUMENTED_OPCODE", MIN_INSTRUMENTED_OPCODE))

fobj.write(DEFINE.format(name, op))

Expand Down
10 changes: 8 additions & 2 deletions Tools/cases_generator/flags.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ class InstructionFlags:
HAS_JUMP_FLAG: bool
HAS_FREE_FLAG: bool
HAS_LOCAL_FLAG: bool
IS_INSTRUMENTED_FLAG: bool

def __post_init__(self):
self.bitmask = {name: (1 << i) for i, name in enumerate(self.names())}
Expand All @@ -38,11 +39,12 @@ def fromInstruction(instr: parsing.Node):
variable_used(instr, "GETLOCAL") or variable_used(instr, "SETLOCAL")
)
and not has_free,
IS_INSTRUMENTED_FLAG=instr.name.startswith("INSTRUMENTED_"),
)

@staticmethod
def newEmpty():
return InstructionFlags(False, False, False, False, False, False)
return InstructionFlags(False, False, False, False, False, False, False)

def add(self, other: "InstructionFlags") -> None:
for name, value in dataclasses.asdict(other).items():
Expand All @@ -68,9 +70,13 @@ def emit_macros(cls, out: Formatter):
out.emit(f"#define {name} ({value})")

for name, value in flags.bitmask.items():
if name == 'IS_INSTRUMENTED_FLAG':
or_special_case = " || ((OP) == INSTRUMENTED_LINE)"
else:
or_special_case = ""
out.emit(
f"#define OPCODE_{name[:-len('_FLAG')]}(OP) "
f"(_PyOpcode_opcode_metadata[OP].flags & ({name}))"
f"(_PyOpcode_opcode_metadata[OP].flags & ({name})){or_special_case}"
)


Expand Down
Loading
0