@@ -581,6 +581,10 @@ _PyCode_Quicken(_Py_CODEUNIT *instructions, Py_ssize_t size, PyObject *consts,
581581#define SPEC_FAIL_BINARY_OP_TRUE_DIVIDE_FLOAT 26
582582#define SPEC_FAIL_BINARY_OP_TRUE_DIVIDE_OTHER 27
583583#define SPEC_FAIL_BINARY_OP_XOR 28
584+ #define SPEC_FAIL_BINARY_OP_OR_INT 29
585+ #define SPEC_FAIL_BINARY_OP_OR_DIFFERENT_TYPES 30
586+ #define SPEC_FAIL_BINARY_OP_XOR_INT 31
587+ #define SPEC_FAIL_BINARY_OP_XOR_DIFFERENT_TYPES 32
584588
585589/* Calls */
586590
@@ -2379,6 +2383,12 @@ binary_op_fail_kind(int oparg, PyObject *lhs, PyObject *rhs)
23792383 return SPEC_FAIL_BINARY_OP_MULTIPLY_OTHER ;
23802384 case NB_OR :
23812385 case NB_INPLACE_OR :
2386+ if (!Py_IS_TYPE (lhs , Py_TYPE (rhs ))) {
2387+ return SPEC_FAIL_BINARY_OP_OR_DIFFERENT_TYPES ;
2388+ }
2389+ if (PyLong_CheckExact (lhs )) {
2390+ return SPEC_FAIL_BINARY_OP_OR_INT ;
2391+ }
23822392 return SPEC_FAIL_BINARY_OP_OR ;
23832393 case NB_POWER :
23842394 case NB_INPLACE_POWER :
@@ -2406,6 +2416,12 @@ binary_op_fail_kind(int oparg, PyObject *lhs, PyObject *rhs)
24062416 return SPEC_FAIL_BINARY_OP_TRUE_DIVIDE_OTHER ;
24072417 case NB_XOR :
24082418 case NB_INPLACE_XOR :
2419+ if (!Py_IS_TYPE (lhs , Py_TYPE (rhs ))) {
2420+ return SPEC_FAIL_BINARY_OP_XOR_DIFFERENT_TYPES ;
2421+ }
2422+ if (PyLong_CheckExact (lhs )) {
2423+ return SPEC_FAIL_BINARY_OP_XOR_INT ;
2424+ }
24092425 return SPEC_FAIL_BINARY_OP_XOR ;
24102426 }
24112427 Py_UNREACHABLE ();
@@ -2414,6 +2430,34 @@ binary_op_fail_kind(int oparg, PyObject *lhs, PyObject *rhs)
24142430
24152431/** Binary Op Specialization Extensions */
24162432
2433+ /* long-long */
2434+
2435+ static inline int
2436+ is_compactlong (PyObject * v )
2437+ {
2438+ return PyLong_CheckExact (v ) &&
2439+ _PyLong_IsCompact ((PyLongObject * )v );
2440+ }
2441+
2442+ static int
2443+ compactlongs_guard (PyObject * lhs , PyObject * rhs )
2444+ {
2445+ return (is_compactlong (lhs ) && is_compactlong (rhs ));
2446+ }
2447+
2448+ #define BITWISE_LONGS_ACTION (NAME , OP ) \
2449+ static PyObject * \
2450+ (NAME)(PyObject *lhs, PyObject *rhs) \
2451+ { \
2452+ Py_ssize_t rhs_val = _PyLong_CompactValue((PyLongObject *)rhs); \
2453+ Py_ssize_t lhs_val = _PyLong_CompactValue((PyLongObject *)lhs); \
2454+ return PyLong_FromSsize_t(lhs_val OP rhs_val); \
2455+ }
2456+ BITWISE_LONGS_ACTION (compactlongs_or , |)
2457+ BITWISE_LONGS_ACTION (compactlongs_and , & )
2458+ BITWISE_LONGS_ACTION (compactlongs_xor , ^)
2459+ #undef BITWISE_LONGS_ACTION
2460+
24172461/* float-long */
24182462
24192463static inline int
@@ -2484,6 +2528,15 @@ LONG_FLOAT_ACTION(compactlong_float_multiply, *)
24842528LONG_FLOAT_ACTION (compactlong_float_true_div , /)
24852529#undef LONG_FLOAT_ACTION
24862530
2531+ static _PyBinaryOpSpecializationDescr compactlongs_specs [NB_OPARG_LAST + 1 ] = {
2532+ [NB_OR ] = {compactlongs_guard , compactlongs_or },
2533+ [NB_AND ] = {compactlongs_guard , compactlongs_and },
2534+ [NB_XOR ] = {compactlongs_guard , compactlongs_xor },
2535+ [NB_INPLACE_OR ] = {compactlongs_guard , compactlongs_or },
2536+ [NB_INPLACE_AND ] = {compactlongs_guard , compactlongs_and },
2537+ [NB_INPLACE_XOR ] = {compactlongs_guard , compactlongs_xor },
2538+ };
2539+
24872540static _PyBinaryOpSpecializationDescr float_compactlong_specs [NB_OPARG_LAST + 1 ] = {
24882541 [NB_ADD ] = {float_compactlong_guard , float_compactlong_add },
24892542 [NB_SUBTRACT ] = {float_compactlong_guard , float_compactlong_subtract },
@@ -2512,6 +2565,7 @@ binary_op_extended_specialization(PyObject *lhs, PyObject *rhs, int oparg,
25122565
25132566 LOOKUP_SPEC (compactlong_float_specs , oparg );
25142567 LOOKUP_SPEC (float_compactlong_specs , oparg );
2568+ LOOKUP_SPEC (compactlongs_specs , oparg );
25152569#undef LOOKUP_SPEC
25162570 return 0 ;
25172571}
0 commit comments