summaryrefslogtreecommitdiffstats
path: root/Modules
diff options
context:
space:
mode:
authorINADA Naoki <methane@users.noreply.github.com>2017-05-11 12:56:42 (GMT)
committerGitHub <noreply@github.com>2017-05-11 12:56:42 (GMT)
commit3dc7c52a9f4fb83be3e26e31e2c7cd9dc1cb41a2 (patch)
tree8b20f9ecf036824ee1e6fbd08b890f4024d7531b /Modules
parenta4465a5bd08f232cf097893006118c82975c3402 (diff)
downloadcpython-3dc7c52a9f4fb83be3e26e31e2c7cd9dc1cb41a2.zip
cpython-3dc7c52a9f4fb83be3e26e31e2c7cd9dc1cb41a2.tar.gz
cpython-3dc7c52a9f4fb83be3e26e31e2c7cd9dc1cb41a2.tar.bz2
bpo-30048: asyncio: fix Task.cancel() was ignored. (GH-1546)
when there are no more `await` or `yield (from)` before return in coroutine, cancel was ignored. example: async def coro(): asyncio.Task.current_task().cancel() return 42 ... res = await coro() # should raise CancelledError (cherry picked from commit 991adca012f5e106c2d4040ce619c696ba6f9c46)
Diffstat (limited to 'Modules')
-rw-r--r--Modules/_asynciomodule.c12
1 files changed, 12 insertions, 0 deletions
diff --git a/Modules/_asynciomodule.c b/Modules/_asynciomodule.c
index a77ff96..75327fa 100644
--- a/Modules/_asynciomodule.c
+++ b/Modules/_asynciomodule.c
@@ -1984,6 +1984,16 @@ task_step_impl(TaskObj *task, PyObject *exc)
if (_PyGen_FetchStopIterationValue(&o) == 0) {
/* The error is StopIteration and that means that
the underlying coroutine has resolved */
+ if (task->task_must_cancel) {
+ // Task is cancelled right before coro stops.
+ Py_DECREF(o);
+ task->task_must_cancel = 0;
+ et = asyncio_CancelledError;
+ Py_INCREF(et);
+ ev = NULL;
+ tb = NULL;
+ goto set_exception;
+ }
PyObject *res = future_set_result((FutureObj*)task, o);
Py_DECREF(o);
if (res == NULL) {
@@ -2001,6 +2011,8 @@ task_step_impl(TaskObj *task, PyObject *exc)
/* Some other exception; pop it and call Task.set_exception() */
PyErr_Fetch(&et, &ev, &tb);
+
+set_exception:
assert(et);
if (!ev || !PyObject_TypeCheck(ev, (PyTypeObject *) et)) {
PyErr_NormalizeException(&et, &ev, &tb);