8000 GH-135379: Specialize int operations for compact ints only by markshannon · Pull Request #135668 · python/cpython · GitHub
[go: up one dir, main page]

Skip to content

GH-135379: Specialize int operations for compact ints only #135668

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

Merged
merged 4 commits into from
Jun 19, 2025
Merged
Show file tree
Hide file tree
Changes from 1 commit
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
Next Next commit
Specialize int operations for compact ints only. Deopts before alloca…
…tion in case of overflow
  • Loading branch information
markshannon committed Jun 18, 2025
commit a7c92fc8b9c8c4c59f943732b4be49b22b714e3e
6 changes: 6 additions & 0 deletions Include/cpython/longintrepr.h
Original file line number Diff line number Diff line change
Expand Up @@ -124,6 +124,12 @@ _PyLong_IsCompact(const PyLongObject* op) {
return op->long_value.lv_tag < (2 << _PyLong_NON_SIZE_BITS);
}

static inline int
PyLong_CheckCompact(const PyObject *op)
{
return PyLong_CheckExact(op) && _PyLong_IsCompact((PyLongObject *)op);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Seems like the cast here should be (const PyLongObject *) instead due to some strict compilers. Let me put up a PR.

}

#define PyUnstable_Long_IsCompact _PyLong_IsCompact

static inline Py_ssize_t
Expand Down
7 changes: 3 additions & 4 deletions Include/internal/pycore_long.h
Original file line number Diff line number Diff line change
Expand Up @@ -112,9 +112,9 @@ PyAPI_DATA(PyObject*) _PyLong_Rshift(PyObject *, int64_t);
// Export for 'math' shared extension
PyAPI_DATA(PyObject*) _PyLong_Lshift(PyObject *, int64_t);

PyAPI_FUNC(PyObject*) _PyCompactLong_Add(PyLongObject *left, PyLongObject *right);
PyAPI_FUNC(PyObject*) _PyCompactLong_Multiply(PyLongObject *left, PyLongObject *right);
PyAPI_FUNC(PyObject*) _PyCompactLong_Subtract(PyLongObject *left, PyLongObject *right);
PyAPI_FUNC(_PyStackRef) _PyCompactLong_Add(PyLongObject *left, PyLongObject *right);
PyAPI_FUNC(_PyStackRef) _PyCompactLong_Multiply(PyLongObject *left, PyLongObject *right);
PyAPI_FUNC(_PyStackRef) _PyCompactLong_Subtract(PyLongObject *left, PyLongObject *right);

// Export for 'binascii' shared extension.
PyAPI_DATA(unsigned char) _PyLong_DigitValue[256];
Expand Down Expand Up @@ -213,7 +213,6 @@ _PyLong_BothAreCompact(const PyLongObject* a, const PyLongObject* b) {
assert(PyLong_Check(b));
return (a->long_value.lv_tag | b->long_value.lv_tag) < (2 << NON_SIZE_BITS);
}

static inline bool
_PyLong_IsZero(const PyLongObject *op)
{
Expand Down
8 changes: 4 additions & 4 deletions Include/internal/pycore_opcode_metadata.h

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

10 changes: 10 additions & 0 deletions Include/internal/pycore_optimizer.h
Original file line number Diff line number Diff line change
Expand Up @@ -178,6 +178,7 @@ typedef enum _JitSymType {
JIT_SYM_KNOWN_VALUE_TAG = 7,
JIT_SYM_TUPLE_TAG = 8,
JIT_SYM_TRUTHINESS_TAG = 9,
JIT_SYM_COMPACT_INT = 10,
} JitSymType;

typedef struct _jit_opt_known_class {
Expand Down Expand Up @@ -210,13 +211,18 @@ typedef struct {
uint16_t value;
} JitOptTruthiness;

typedef struct {
uint8_t tag;
} JitOptCompactInt;

typedef union _jit_opt_symbol {
uint8_t tag;
JitOptKnownClass cls;
JitOptKnownValue value;
JitOptKnownVersion version;
JitOptTuple tuple;
JitOptTruthiness truthiness;
JitOptCompactInt compact;
} JitOptSymbol;


Expand Down Expand Up @@ -282,6 +288,10 @@ extern JitOptSymbol *_Py_uop_sym_new_tuple(JitOptContext *ctx, int size, JitOptS
extern JitOptSymbol *_Py_uop_sym_tuple_getitem(JitOptContext *ctx, JitOptSymbol *sym, int item);
extern int _Py_uop_sym_tuple_length(JitOptSymbol *sym);
extern JitOptSymbol *_Py_uop_sym_new_truthiness(JitOptContext *ctx, JitOptSymbol *value, bool truthy);
extern bool _Py_uop_sym_is_compact_int(JitOptSymbol *sym);
extern JitOptSymbol *_Py_uop_sym_new_compact_int(JitOptContext *ctx);
extern void _Py_uop_sym_set_compact_int(JitOptContext *ctx, JitOptSymbol *value);


extern void _Py_uop_abstractcontext_init(JitOptContext *ctx);
extern void _Py_uop_abstractcontext_fini(JitOptContext *ctx);
Expand Down
Loading
0