]> git.ipfire.org Git - thirdparty/Python/cpython.git/commitdiff
gh-98831: rewrite BEFORE_ASYNC_WITH and END_ASYNC_FOR in the instruction definition...
authorIrit Katriel <1055913+iritkatriel@users.noreply.github.com>
Tue, 31 Jan 2023 18:47:50 +0000 (18:47 +0000)
committerGitHub <noreply@github.com>
Tue, 31 Jan 2023 18:47:50 +0000 (18:47 +0000)
Python/bytecodes.c
Python/generated_cases.c.h
Python/opcode_metadata.h

index 5b3bf4ec7ba7960aaf25e14fa37954d19df6bff1..336088e08197debf438aba15dcf866d588e41393 100644 (file)
@@ -770,18 +770,16 @@ dummy_func(
             ERROR_IF(val == NULL, error);
         }
 
-        // stack effect: (__0, __1 -- )
-        inst(END_ASYNC_FOR) {
-            PyObject *val = POP();
-            assert(val && PyExceptionInstance_Check(val));
-            if (PyErr_GivenExceptionMatches(val, PyExc_StopAsyncIteration)) {
-                Py_DECREF(val);
-                Py_DECREF(POP());
+        inst(END_ASYNC_FOR, (awaitable, exc -- )) {
+            assert(exc && PyExceptionInstance_Check(exc));
+            if (PyErr_GivenExceptionMatches(exc, PyExc_StopAsyncIteration)) {
+                DECREF_INPUTS();
             }
             else {
-                PyObject *exc = Py_NewRef(PyExceptionInstance_Class(val));
-                PyObject *tb = PyException_GetTraceback(val);
-                _PyErr_Restore(tstate, exc, val, tb);
+                Py_INCREF(exc);
+                PyObject *typ = Py_NewRef(PyExceptionInstance_Class(exc));
+                PyObject *tb = PyException_GetTraceback(exc);
+                _PyErr_Restore(tstate, typ, exc, tb);
                 goto exception_unwind;
             }
         }
@@ -2266,10 +2264,7 @@ dummy_func(
             DISPATCH_INLINED(gen_frame);
         }
 
-        // stack effect: ( -- __0)
-        inst(BEFORE_ASYNC_WITH) {
-            PyObject *mgr = TOP();
-            PyObject *res;
+        inst(BEFORE_ASYNC_WITH, (mgr -- exit, res)) {
             PyObject *enter = _PyObject_LookupSpecial(mgr, &_Py_ID(__aenter__));
             if (enter == NULL) {
                 if (!_PyErr_Occurred(tstate)) {
@@ -2280,7 +2275,7 @@ dummy_func(
                 }
                 goto error;
             }
-            PyObject *exit = _PyObject_LookupSpecial(mgr, &_Py_ID(__aexit__));
+            exit = _PyObject_LookupSpecial(mgr, &_Py_ID(__aexit__));
             if (exit == NULL) {
                 if (!_PyErr_Occurred(tstate)) {
                     _PyErr_Format(tstate, PyExc_TypeError,
@@ -2292,13 +2287,13 @@ dummy_func(
                 Py_DECREF(enter);
                 goto error;
             }
-            SET_TOP(exit);
-            Py_DECREF(mgr);
+            DECREF_INPUTS();
             res = _PyObject_CallNoArgs(enter);
             Py_DECREF(enter);
-            if (res == NULL)
-                goto error;
-            PUSH(res);
+            if (res == NULL) {
+                Py_DECREF(exit);
+                ERROR_IF(true, error);
+            }
             PREDICT(GET_AWAITABLE);
         }
 
index 661fe27f327b33027f413f56198eeb95151b5dc2..d70d64ecbdd5c107fce5cf5cf779ffec559cf6cd 100644 (file)
         }
 
         TARGET(END_ASYNC_FOR) {
-            PyObject *val = POP();
-            assert(val && PyExceptionInstance_Check(val));
-            if (PyErr_GivenExceptionMatches(val, PyExc_StopAsyncIteration)) {
-                Py_DECREF(val);
-                Py_DECREF(POP());
+            PyObject *exc = PEEK(1);
+            PyObject *awaitable = PEEK(2);
+            assert(exc && PyExceptionInstance_Check(exc));
+            if (PyErr_GivenExceptionMatches(exc, PyExc_StopAsyncIteration)) {
+                Py_DECREF(awaitable);
+                Py_DECREF(exc);
             }
             else {
-                PyObject *exc = Py_NewRef(PyExceptionInstance_Class(val));
-                PyObject *tb = PyException_GetTraceback(val);
-                _PyErr_Restore(tstate, exc, val, tb);
+                Py_INCREF(exc);
+                PyObject *typ = Py_NewRef(PyExceptionInstance_Class(exc));
+                PyObject *tb = PyException_GetTraceback(exc);
+                _PyErr_Restore(tstate, typ, exc, tb);
                 goto exception_unwind;
             }
+            STACK_SHRINK(2);
             DISPATCH();
         }
 
         }
 
         TARGET(BEFORE_ASYNC_WITH) {
-            PyObject *mgr = TOP();
+            PyObject *mgr = PEEK(1);
+            PyObject *exit;
             PyObject *res;
             PyObject *enter = _PyObject_LookupSpecial(mgr, &_Py_ID(__aenter__));
             if (enter == NULL) {
                 }
                 goto error;
             }
-            PyObject *exit = _PyObject_LookupSpecial(mgr, &_Py_ID(__aexit__));
+            exit = _PyObject_LookupSpecial(mgr, &_Py_ID(__aexit__));
             if (exit == NULL) {
                 if (!_PyErr_Occurred(tstate)) {
                     _PyErr_Format(tstate, PyExc_TypeError,
                 Py_DECREF(enter);
                 goto error;
             }
-            SET_TOP(exit);
             Py_DECREF(mgr);
             res = _PyObject_CallNoArgs(enter);
             Py_DECREF(enter);
-            if (res == NULL)
-                goto error;
-            PUSH(res);
+            if (res == NULL) {
+                Py_DECREF(exit);
+                if (true) goto pop_1_error;
+            }
+            STACK_GROW(1);
+            POKE(1, res);
+            POKE(2, exit);
             PREDICT(GET_AWAITABLE);
             DISPATCH();
         }
index c40e40ff324d11ffd61dc166ee7bd3c5b2577d1b..171fed363d3be056c27c449de948c630f974b915 100644 (file)
@@ -109,7 +109,7 @@ _PyOpcode_num_popped(int opcode, int oparg) {
         case PREP_RERAISE_STAR:
             return 2;
         case END_ASYNC_FOR:
-            return -1;
+            return 2;
         case CLEANUP_THROW:
             return -1;
         case LOAD_ASSERTION_ERROR:
@@ -271,7 +271,7 @@ _PyOpcode_num_popped(int opcode, int oparg) {
         case FOR_ITER_GEN:
             return -1;
         case BEFORE_ASYNC_WITH:
-            return -1;
+            return 1;
         case BEFORE_WITH:
             return 1;
         case WITH_EXCEPT_START:
@@ -455,7 +455,7 @@ _PyOpcode_num_pushed(int opcode, int oparg) {
         case PREP_RERAISE_STAR:
             return 1;
         case END_ASYNC_FOR:
-            return -1;
+            return 0;
         case CLEANUP_THROW:
             return -1;
         case LOAD_ASSERTION_ERROR:
@@ -617,7 +617,7 @@ _PyOpcode_num_pushed(int opcode, int oparg) {
         case FOR_ITER_GEN:
             return -1;
         case BEFORE_ASYNC_WITH:
-            return -1;
+            return 2;
         case BEFORE_WITH:
             return 2;
         case WITH_EXCEPT_START: