]> git.ipfire.org Git - thirdparty/Python/cpython.git/commitdiff
GH-100110: Specialize FOR_ITER for tuples (GH-100109)
authorKen Jin <kenjin@python.org>
Fri, 9 Dec 2022 10:27:01 +0000 (18:27 +0800)
committerGitHub <noreply@github.com>
Fri, 9 Dec 2022 10:27:01 +0000 (10:27 +0000)
* Specialize FOR_ITER for tuples

Include/internal/pycore_opcode.h
Include/internal/pycore_tuple.h
Include/opcode.h
Lib/opcode.py
Misc/NEWS.d/next/Core and Builtins/2022-12-08-12-26-34.gh-issue-100110.ertac-.rst [new file with mode: 0644]
Objects/tupleobject.c
Python/bytecodes.c
Python/generated_cases.c.h
Python/opcode_targets.h
Python/specialize.c

index 0d31ca166a7d2e32895e0daa813fc5e213b82e60..da8a272f2fa2d0e6b92bd0992e7f977cbb090255 100644 (file)
@@ -125,6 +125,7 @@ const uint8_t _PyOpcode_Deopt[256] = {
     [FOR_ITER_GEN] = FOR_ITER,
     [FOR_ITER_LIST] = FOR_ITER,
     [FOR_ITER_RANGE] = FOR_ITER,
+    [FOR_ITER_TUPLE] = FOR_ITER,
     [GET_AITER] = GET_AITER,
     [GET_ANEXT] = GET_ANEXT,
     [GET_AWAITABLE] = GET_AWAITABLE,
@@ -293,31 +294,31 @@ static const char *const _PyOpcode_OpName[263] = {
     [FOR_ITER_LIST] = "FOR_ITER_LIST",
     [STORE_SUBSCR] = "STORE_SUBSCR",
     [DELETE_SUBSCR] = "DELETE_SUBSCR",
-    [FOR_ITER_RANGE] = "FOR_ITER_RANGE",
+    [FOR_ITER_TUPLE] = "FOR_ITER_TUPLE",
     [STOPITERATION_ERROR] = "STOPITERATION_ERROR",
+    [FOR_ITER_RANGE] = "FOR_ITER_RANGE",
     [FOR_ITER_GEN] = "FOR_ITER_GEN",
     [LOAD_ATTR_CLASS] = "LOAD_ATTR_CLASS",
     [LOAD_ATTR_GETATTRIBUTE_OVERRIDDEN] = "LOAD_ATTR_GETATTRIBUTE_OVERRIDDEN",
-    [LOAD_ATTR_INSTANCE_VALUE] = "LOAD_ATTR_INSTANCE_VALUE",
     [GET_ITER] = "GET_ITER",
     [GET_YIELD_FROM_ITER] = "GET_YIELD_FROM_ITER",
     [PRINT_EXPR] = "PRINT_EXPR",
     [LOAD_BUILD_CLASS] = "LOAD_BUILD_CLASS",
+    [LOAD_ATTR_INSTANCE_VALUE] = "LOAD_ATTR_INSTANCE_VALUE",
     [LOAD_ATTR_MODULE] = "LOAD_ATTR_MODULE",
-    [LOAD_ATTR_PROPERTY] = "LOAD_ATTR_PROPERTY",
     [LOAD_ASSERTION_ERROR] = "LOAD_ASSERTION_ERROR",
     [RETURN_GENERATOR] = "RETURN_GENERATOR",
+    [LOAD_ATTR_PROPERTY] = "LOAD_ATTR_PROPERTY",
     [LOAD_ATTR_SLOT] = "LOAD_ATTR_SLOT",
     [LOAD_ATTR_WITH_HINT] = "LOAD_ATTR_WITH_HINT",
     [LOAD_ATTR_METHOD_LAZY_DICT] = "LOAD_ATTR_METHOD_LAZY_DICT",
     [LOAD_ATTR_METHOD_NO_DICT] = "LOAD_ATTR_METHOD_NO_DICT",
     [LOAD_ATTR_METHOD_WITH_DICT] = "LOAD_ATTR_METHOD_WITH_DICT",
-    [LOAD_ATTR_METHOD_WITH_VALUES] = "LOAD_ATTR_METHOD_WITH_VALUES",
     [LIST_TO_TUPLE] = "LIST_TO_TUPLE",
     [RETURN_VALUE] = "RETURN_VALUE",
     [IMPORT_STAR] = "IMPORT_STAR",
     [SETUP_ANNOTATIONS] = "SETUP_ANNOTATIONS",
-    [LOAD_CONST__LOAD_FAST] = "LOAD_CONST__LOAD_FAST",
+    [LOAD_ATTR_METHOD_WITH_VALUES] = "LOAD_ATTR_METHOD_WITH_VALUES",
     [ASYNC_GEN_WRAP] = "ASYNC_GEN_WRAP",
     [PREP_RERAISE_STAR] = "PREP_RERAISE_STAR",
     [POP_EXCEPT] = "POP_EXCEPT",
@@ -344,7 +345,7 @@ static const char *const _PyOpcode_OpName[263] = {
     [JUMP_FORWARD] = "JUMP_FORWARD",
     [JUMP_IF_FALSE_OR_POP] = "JUMP_IF_FALSE_OR_POP",
     [JUMP_IF_TRUE_OR_POP] = "JUMP_IF_TRUE_OR_POP",
-    [LOAD_FAST__LOAD_CONST] = "LOAD_FAST__LOAD_CONST",
+    [LOAD_CONST__LOAD_FAST] = "LOAD_CONST__LOAD_FAST",
     [POP_JUMP_IF_FALSE] = "POP_JUMP_IF_FALSE",
     [POP_JUMP_IF_TRUE] = "POP_JUMP_IF_TRUE",
     [LOAD_GLOBAL] = "LOAD_GLOBAL",
@@ -352,7 +353,7 @@ static const char *const _PyOpcode_OpName[263] = {
     [CONTAINS_OP] = "CONTAINS_OP",
     [RERAISE] = "RERAISE",
     [COPY] = "COPY",
-    [LOAD_FAST__LOAD_FAST] = "LOAD_FAST__LOAD_FAST",
+    [LOAD_FAST__LOAD_CONST] = "LOAD_FAST__LOAD_CONST",
     [BINARY_OP] = "BINARY_OP",
     [SEND] = "SEND",
     [LOAD_FAST] = "LOAD_FAST",
@@ -372,9 +373,9 @@ static const char *const _PyOpcode_OpName[263] = {
     [STORE_DEREF] = "STORE_DEREF",
     [DELETE_DEREF] = "DELETE_DEREF",
     [JUMP_BACKWARD] = "JUMP_BACKWARD",
-    [LOAD_GLOBAL_BUILTIN] = "LOAD_GLOBAL_BUILTIN",
+    [LOAD_FAST__LOAD_FAST] = "LOAD_FAST__LOAD_FAST",
     [CALL_FUNCTION_EX] = "CALL_FUNCTION_EX",
-    [LOAD_GLOBAL_MODULE] = "LOAD_GLOBAL_MODULE",
+    [LOAD_GLOBAL_BUILTIN] = "LOAD_GLOBAL_BUILTIN",
     [EXTENDED_ARG] = "EXTENDED_ARG",
     [LIST_APPEND] = "LIST_APPEND",
     [SET_ADD] = "SET_ADD",
@@ -384,24 +385,24 @@ static const char *const _PyOpcode_OpName[263] = {
     [YIELD_VALUE] = "YIELD_VALUE",
     [RESUME] = "RESUME",
     [MATCH_CLASS] = "MATCH_CLASS",
+    [LOAD_GLOBAL_MODULE] = "LOAD_GLOBAL_MODULE",
     [STORE_ATTR_INSTANCE_VALUE] = "STORE_ATTR_INSTANCE_VALUE",
-    [STORE_ATTR_SLOT] = "STORE_ATTR_SLOT",
     [FORMAT_VALUE] = "FORMAT_VALUE",
     [BUILD_CONST_KEY_MAP] = "BUILD_CONST_KEY_MAP",
     [BUILD_STRING] = "BUILD_STRING",
+    [STORE_ATTR_SLOT] = "STORE_ATTR_SLOT",
     [STORE_ATTR_WITH_HINT] = "STORE_ATTR_WITH_HINT",
     [STORE_FAST__LOAD_FAST] = "STORE_FAST__LOAD_FAST",
     [STORE_FAST__STORE_FAST] = "STORE_FAST__STORE_FAST",
-    [STORE_SUBSCR_DICT] = "STORE_SUBSCR_DICT",
     [LIST_EXTEND] = "LIST_EXTEND",
     [SET_UPDATE] = "SET_UPDATE",
     [DICT_MERGE] = "DICT_MERGE",
     [DICT_UPDATE] = "DICT_UPDATE",
+    [STORE_SUBSCR_DICT] = "STORE_SUBSCR_DICT",
     [STORE_SUBSCR_LIST_INT] = "STORE_SUBSCR_LIST_INT",
     [UNPACK_SEQUENCE_LIST] = "UNPACK_SEQUENCE_LIST",
     [UNPACK_SEQUENCE_TUPLE] = "UNPACK_SEQUENCE_TUPLE",
     [UNPACK_SEQUENCE_TWO_TUPLE] = "UNPACK_SEQUENCE_TWO_TUPLE",
-    [170] = "<170>",
     [CALL] = "CALL",
     [KW_NAMES] = "KW_NAMES",
     [173] = "<173>",
@@ -498,7 +499,6 @@ static const char *const _PyOpcode_OpName[263] = {
 #endif
 
 #define EXTRA_CASES \
-    case 170: \
     case 173: \
     case 174: \
     case 175: \
index 504c36338d9e9698db756ddb3a1abf3545ae4aa7..edc70843b5753173de0a17bd01123429d79b4e5c 100644 (file)
@@ -67,6 +67,13 @@ struct _Py_tuple_state {
 extern PyObject *_PyTuple_FromArray(PyObject *const *, Py_ssize_t);
 extern PyObject *_PyTuple_FromArraySteal(PyObject *const *, Py_ssize_t);
 
+
+typedef struct {
+    PyObject_HEAD
+    Py_ssize_t it_index;
+    PyTupleObject *it_seq; /* Set to NULL when iterator is exhausted */
+} _PyTupleIterObject;
+
 #ifdef __cplusplus
 }
 #endif
index f284313d2ed756ca9371db2422bf7a8be07d5011..888250ed37e8cbe8945bc94704c1200aa4bdb07c 100644 (file)
@@ -162,34 +162,35 @@ extern "C" {
 #define COMPARE_OP_INT_JUMP                     57
 #define COMPARE_OP_STR_JUMP                     58
 #define FOR_ITER_LIST                           59
-#define FOR_ITER_RANGE                          62
-#define FOR_ITER_GEN                            64
-#define LOAD_ATTR_CLASS                         65
-#define LOAD_ATTR_GETATTRIBUTE_OVERRIDDEN       66
-#define LOAD_ATTR_INSTANCE_VALUE                67
-#define LOAD_ATTR_MODULE                        72
-#define LOAD_ATTR_PROPERTY                      73
-#define LOAD_ATTR_SLOT                          76
-#define LOAD_ATTR_WITH_HINT                     77
-#define LOAD_ATTR_METHOD_LAZY_DICT              78
-#define LOAD_ATTR_METHOD_NO_DICT                79
-#define LOAD_ATTR_METHOD_WITH_DICT              80
-#define LOAD_ATTR_METHOD_WITH_VALUES            81
-#define LOAD_CONST__LOAD_FAST                   86
-#define LOAD_FAST__LOAD_CONST                  113
-#define LOAD_FAST__LOAD_FAST                   121
-#define LOAD_GLOBAL_BUILTIN                    141
-#define LOAD_GLOBAL_MODULE                     143
-#define STORE_ATTR_INSTANCE_VALUE              153
-#define STORE_ATTR_SLOT                        154
-#define STORE_ATTR_WITH_HINT                   158
-#define STORE_FAST__LOAD_FAST                  159
-#define STORE_FAST__STORE_FAST                 160
-#define STORE_SUBSCR_DICT                      161
-#define STORE_SUBSCR_LIST_INT                  166
-#define UNPACK_SEQUENCE_LIST                   167
-#define UNPACK_SEQUENCE_TUPLE                  168
-#define UNPACK_SEQUENCE_TWO_TUPLE              169
+#define FOR_ITER_TUPLE                          62
+#define FOR_ITER_RANGE                          64
+#define FOR_ITER_GEN                            65
+#define LOAD_ATTR_CLASS                         66
+#define LOAD_ATTR_GETATTRIBUTE_OVERRIDDEN       67
+#define LOAD_ATTR_INSTANCE_VALUE                72
+#define LOAD_ATTR_MODULE                        73
+#define LOAD_ATTR_PROPERTY                      76
+#define LOAD_ATTR_SLOT                          77
+#define LOAD_ATTR_WITH_HINT                     78
+#define LOAD_ATTR_METHOD_LAZY_DICT              79
+#define LOAD_ATTR_METHOD_NO_DICT                80
+#define LOAD_ATTR_METHOD_WITH_DICT              81
+#define LOAD_ATTR_METHOD_WITH_VALUES            86
+#define LOAD_CONST__LOAD_FAST                  113
+#define LOAD_FAST__LOAD_CONST                  121
+#define LOAD_FAST__LOAD_FAST                   141
+#define LOAD_GLOBAL_BUILTIN                    143
+#define LOAD_GLOBAL_MODULE                     153
+#define STORE_ATTR_INSTANCE_VALUE              154
+#define STORE_ATTR_SLOT                        158
+#define STORE_ATTR_WITH_HINT                   159
+#define STORE_FAST__LOAD_FAST                  160
+#define STORE_FAST__STORE_FAST                 161
+#define STORE_SUBSCR_DICT                      166
+#define STORE_SUBSCR_LIST_INT                  167
+#define UNPACK_SEQUENCE_LIST                   168
+#define UNPACK_SEQUENCE_TUPLE                  169
+#define UNPACK_SEQUENCE_TWO_TUPLE              170
 #define DO_TRACING                             255
 
 #define HAS_ARG(op) ((((op) >= HAVE_ARGUMENT) && (!IS_PSEUDO_OPCODE(op)))\
index fa6dbe5d24170cce43572440363ba12bf8272028..fc57affbac58142d7f55cba1ec20ad08c30f16b0 100644 (file)
@@ -320,6 +320,7 @@ _specializations = {
     ],
     "FOR_ITER": [
         "FOR_ITER_LIST",
+        "FOR_ITER_TUPLE",
         "FOR_ITER_RANGE",
         "FOR_ITER_GEN",
     ],
diff --git a/Misc/NEWS.d/next/Core and Builtins/2022-12-08-12-26-34.gh-issue-100110.ertac-.rst b/Misc/NEWS.d/next/Core and Builtins/2022-12-08-12-26-34.gh-issue-100110.ertac-.rst
new file mode 100644 (file)
index 0000000..e494f44
--- /dev/null
@@ -0,0 +1 @@
+Specialize ``FOR_ITER`` for tuples.
index 4405125d45e7cca11f3b70f8b811ab431267f5a9..e1b9953226c0d749e3f27ac55b840ebbefcbf776 100644 (file)
@@ -995,14 +995,9 @@ _PyTuple_ClearFreeList(PyInterpreterState *interp)
 
 /*********************** Tuple Iterator **************************/
 
-typedef struct {
-    PyObject_HEAD
-    Py_ssize_t it_index;
-    PyTupleObject *it_seq; /* Set to NULL when iterator is exhausted */
-} tupleiterobject;
 
 static void
-tupleiter_dealloc(tupleiterobject *it)
+tupleiter_dealloc(_PyTupleIterObject *it)
 {
     _PyObject_GC_UNTRACK(it);
     Py_XDECREF(it->it_seq);
@@ -1010,14 +1005,14 @@ tupleiter_dealloc(tupleiterobject *it)
 }
 
 static int
-tupleiter_traverse(tupleiterobject *it, visitproc visit, void *arg)
+tupleiter_traverse(_PyTupleIterObject *it, visitproc visit, void *arg)
 {
     Py_VISIT(it->it_seq);
     return 0;
 }
 
 static PyObject *
-tupleiter_next(tupleiterobject *it)
+tupleiter_next(_PyTupleIterObject *it)
 {
     PyTupleObject *seq;
     PyObject *item;
@@ -1040,7 +1035,7 @@ tupleiter_next(tupleiterobject *it)
 }
 
 static PyObject *
-tupleiter_len(tupleiterobject *it, PyObject *Py_UNUSED(ignored))
+tupleiter_len(_PyTupleIterObject *it, PyObject *Py_UNUSED(ignored))
 {
     Py_ssize_t len = 0;
     if (it->it_seq)
@@ -1051,7 +1046,7 @@ tupleiter_len(tupleiterobject *it, PyObject *Py_UNUSED(ignored))
 PyDoc_STRVAR(length_hint_doc, "Private method returning an estimate of len(list(it)).");
 
 static PyObject *
-tupleiter_reduce(tupleiterobject *it, PyObject *Py_UNUSED(ignored))
+tupleiter_reduce(_PyTupleIterObject *it, PyObject *Py_UNUSED(ignored))
 {
     if (it->it_seq)
         return Py_BuildValue("N(O)n", _PyEval_GetBuiltin(&_Py_ID(iter)),
@@ -1061,7 +1056,7 @@ tupleiter_reduce(tupleiterobject *it, PyObject *Py_UNUSED(ignored))
 }
 
 static PyObject *
-tupleiter_setstate(tupleiterobject *it, PyObject *state)
+tupleiter_setstate(_PyTupleIterObject *it, PyObject *state)
 {
     Py_ssize_t index = PyLong_AsSsize_t(state);
     if (index == -1 && PyErr_Occurred())
@@ -1089,7 +1084,7 @@ static PyMethodDef tupleiter_methods[] = {
 PyTypeObject PyTupleIter_Type = {
     PyVarObject_HEAD_INIT(&PyType_Type, 0)
     "tuple_iterator",                           /* tp_name */
-    sizeof(tupleiterobject),                    /* tp_basicsize */
+    sizeof(_PyTupleIterObject),                    /* tp_basicsize */
     0,                                          /* tp_itemsize */
     /* methods */
     (destructor)tupleiter_dealloc,              /* tp_dealloc */
@@ -1122,13 +1117,13 @@ PyTypeObject PyTupleIter_Type = {
 static PyObject *
 tuple_iter(PyObject *seq)
 {
-    tupleiterobject *it;
+    _PyTupleIterObject *it;
 
     if (!PyTuple_Check(seq)) {
         PyErr_BadInternalCall();
         return NULL;
     }
-    it = PyObject_GC_New(tupleiterobject, &PyTupleIter_Type);
+    it = PyObject_GC_New(_PyTupleIterObject, &PyTupleIter_Type);
     if (it == NULL)
         return NULL;
     it->it_index = 0;
index 7a1bfdcc9e26e8d879eb83bbc93fdc17f8aa0591..5807bd5dc2d29c6415ff748de9ea63555216e5fd 100644 (file)
@@ -2523,6 +2523,29 @@ dummy_func(
         end_for_iter_list:
         }
 
+        // stack effect: ( -- __0)
+        inst(FOR_ITER_TUPLE) {
+            assert(cframe.use_tracing == 0);
+            _PyTupleIterObject *it = (_PyTupleIterObject *)TOP();
+            DEOPT_IF(Py_TYPE(it) != &PyTupleIter_Type, FOR_ITER);
+            STAT_INC(FOR_ITER, hit);
+            PyTupleObject *seq = it->it_seq;
+            if (seq) {
+                if (it->it_index < PyTuple_GET_SIZE(seq)) {
+                    PyObject *next = PyTuple_GET_ITEM(seq, it->it_index++);
+                    PUSH(Py_NewRef(next));
+                    JUMPBY(INLINE_CACHE_ENTRIES_FOR_ITER);
+                    goto end_for_iter_tuple;  // End of this instruction
+                }
+                it->it_seq = NULL;
+                Py_DECREF(seq);
+            }
+            STACK_SHRINK(1);
+            Py_DECREF(it);
+            JUMPBY(INLINE_CACHE_ENTRIES_FOR_ITER + oparg + 1);
+        end_for_iter_tuple:
+        }
+
         // stack effect: ( -- __0)
         inst(FOR_ITER_RANGE) {
             assert(cframe.use_tracing == 0);
index 76eb6085ec57c154838d7ee5e1411776711e9360..59e70b7222696587f01d7b138442e51a5b6cf8ee 100644 (file)
             DISPATCH();
         }
 
+        TARGET(FOR_ITER_TUPLE) {
+            assert(cframe.use_tracing == 0);
+            _PyTupleIterObject *it = (_PyTupleIterObject *)TOP();
+            DEOPT_IF(Py_TYPE(it) != &PyTupleIter_Type, FOR_ITER);
+            STAT_INC(FOR_ITER, hit);
+            PyTupleObject *seq = it->it_seq;
+            if (seq) {
+                if (it->it_index < PyTuple_GET_SIZE(seq)) {
+                    PyObject *next = PyTuple_GET_ITEM(seq, it->it_index++);
+                    PUSH(Py_NewRef(next));
+                    JUMPBY(INLINE_CACHE_ENTRIES_FOR_ITER);
+                    goto end_for_iter_tuple;  // End of this instruction
+                }
+                it->it_seq = NULL;
+                Py_DECREF(seq);
+            }
+            STACK_SHRINK(1);
+            Py_DECREF(it);
+            JUMPBY(INLINE_CACHE_ENTRIES_FOR_ITER + oparg + 1);
+        end_for_iter_tuple:
+            DISPATCH();
+        }
+
         TARGET(FOR_ITER_RANGE) {
             assert(cframe.use_tracing == 0);
             _PyRangeIterObject *r = (_PyRangeIterObject *)TOP();
index 3aba4e7556a65f9e75f090d707c47a5867abbca2..be3ad01c151c043d7d73eb17f2808d2dfac3e67f 100644 (file)
@@ -61,31 +61,31 @@ static void *opcode_targets[256] = {
     &&TARGET_FOR_ITER_LIST,
     &&TARGET_STORE_SUBSCR,
     &&TARGET_DELETE_SUBSCR,
-    &&TARGET_FOR_ITER_RANGE,
+    &&TARGET_FOR_ITER_TUPLE,
     &&TARGET_STOPITERATION_ERROR,
+    &&TARGET_FOR_ITER_RANGE,
     &&TARGET_FOR_ITER_GEN,
     &&TARGET_LOAD_ATTR_CLASS,
     &&TARGET_LOAD_ATTR_GETATTRIBUTE_OVERRIDDEN,
-    &&TARGET_LOAD_ATTR_INSTANCE_VALUE,
     &&TARGET_GET_ITER,
     &&TARGET_GET_YIELD_FROM_ITER,
     &&TARGET_PRINT_EXPR,
     &&TARGET_LOAD_BUILD_CLASS,
+    &&TARGET_LOAD_ATTR_INSTANCE_VALUE,
     &&TARGET_LOAD_ATTR_MODULE,
-    &&TARGET_LOAD_ATTR_PROPERTY,
     &&TARGET_LOAD_ASSERTION_ERROR,
     &&TARGET_RETURN_GENERATOR,
+    &&TARGET_LOAD_ATTR_PROPERTY,
     &&TARGET_LOAD_ATTR_SLOT,
     &&TARGET_LOAD_ATTR_WITH_HINT,
     &&TARGET_LOAD_ATTR_METHOD_LAZY_DICT,
     &&TARGET_LOAD_ATTR_METHOD_NO_DICT,
     &&TARGET_LOAD_ATTR_METHOD_WITH_DICT,
-    &&TARGET_LOAD_ATTR_METHOD_WITH_VALUES,
     &&TARGET_LIST_TO_TUPLE,
     &&TARGET_RETURN_VALUE,
     &&TARGET_IMPORT_STAR,
     &&TARGET_SETUP_ANNOTATIONS,
-    &&TARGET_LOAD_CONST__LOAD_FAST,
+    &&TARGET_LOAD_ATTR_METHOD_WITH_VALUES,
     &&TARGET_ASYNC_GEN_WRAP,
     &&TARGET_PREP_RERAISE_STAR,
     &&TARGET_POP_EXCEPT,
@@ -112,7 +112,7 @@ static void *opcode_targets[256] = {
     &&TARGET_JUMP_FORWARD,
     &&TARGET_JUMP_IF_FALSE_OR_POP,
     &&TARGET_JUMP_IF_TRUE_OR_POP,
-    &&TARGET_LOAD_FAST__LOAD_CONST,
+    &&TARGET_LOAD_CONST__LOAD_FAST,
     &&TARGET_POP_JUMP_IF_FALSE,
     &&TARGET_POP_JUMP_IF_TRUE,
     &&TARGET_LOAD_GLOBAL,
@@ -120,7 +120,7 @@ static void *opcode_targets[256] = {
     &&TARGET_CONTAINS_OP,
     &&TARGET_RERAISE,
     &&TARGET_COPY,
-    &&TARGET_LOAD_FAST__LOAD_FAST,
+    &&TARGET_LOAD_FAST__LOAD_CONST,
     &&TARGET_BINARY_OP,
     &&TARGET_SEND,
     &&TARGET_LOAD_FAST,
@@ -140,9 +140,9 @@ static void *opcode_targets[256] = {
     &&TARGET_STORE_DEREF,
     &&TARGET_DELETE_DEREF,
     &&TARGET_JUMP_BACKWARD,
-    &&TARGET_LOAD_GLOBAL_BUILTIN,
+    &&TARGET_LOAD_FAST__LOAD_FAST,
     &&TARGET_CALL_FUNCTION_EX,
-    &&TARGET_LOAD_GLOBAL_MODULE,
+    &&TARGET_LOAD_GLOBAL_BUILTIN,
     &&TARGET_EXTENDED_ARG,
     &&TARGET_LIST_APPEND,
     &&TARGET_SET_ADD,
@@ -152,24 +152,24 @@ static void *opcode_targets[256] = {
     &&TARGET_YIELD_VALUE,
     &&TARGET_RESUME,
     &&TARGET_MATCH_CLASS,
+    &&TARGET_LOAD_GLOBAL_MODULE,
     &&TARGET_STORE_ATTR_INSTANCE_VALUE,
-    &&TARGET_STORE_ATTR_SLOT,
     &&TARGET_FORMAT_VALUE,
     &&TARGET_BUILD_CONST_KEY_MAP,
     &&TARGET_BUILD_STRING,
+    &&TARGET_STORE_ATTR_SLOT,
     &&TARGET_STORE_ATTR_WITH_HINT,
     &&TARGET_STORE_FAST__LOAD_FAST,
     &&TARGET_STORE_FAST__STORE_FAST,
-    &&TARGET_STORE_SUBSCR_DICT,
     &&TARGET_LIST_EXTEND,
     &&TARGET_SET_UPDATE,
     &&TARGET_DICT_MERGE,
     &&TARGET_DICT_UPDATE,
+    &&TARGET_STORE_SUBSCR_DICT,
     &&TARGET_STORE_SUBSCR_LIST_INT,
     &&TARGET_UNPACK_SEQUENCE_LIST,
     &&TARGET_UNPACK_SEQUENCE_TUPLE,
     &&TARGET_UNPACK_SEQUENCE_TWO_TUPLE,
-    &&_unknown_opcode,
     &&TARGET_CALL,
     &&TARGET_KW_NAMES,
     &&_unknown_opcode,
index cd09b188b7fa97e6ba445efbb1bcdf9908932f32..7545a7712493e6aa1585dce958b7b9a825318d8f 100644 (file)
@@ -2132,6 +2132,10 @@ _Py_Specialize_ForIter(PyObject *iter, _Py_CODEUNIT *instr, int oparg)
         _Py_SET_OPCODE(*instr, FOR_ITER_LIST);
         goto success;
     }
+    else if (tp == &PyTupleIter_Type) {
+        _Py_SET_OPCODE(*instr, FOR_ITER_TUPLE);
+        goto success;
+    }
     else if (tp == &PyRangeIter_Type && next_op == STORE_FAST) {
         _Py_SET_OPCODE(*instr, FOR_ITER_RANGE);
         goto success;