kore

An easy to use, scalable and secure web application framework for writing web APIs in C.
Commits | Files | Refs | README | LICENSE | git clone https://git.kore.io/kore.git

commit 7b5046873a60e51571fd043f0a1c9da5f266d14c
parent ebee0f375238618721d888212e4c72f06af1941d
Author: Joris Vink <joris@coders.se>
Date:   Tue, 29 Oct 2019 15:12:20 +0100

Make sure we wakeup the coroutine that called proc.reap().

We actually woke up the coroutine that originally spawned the process
when we reap it, but another coroutine may have taken over the object.

This mimics how we do things for the pysock_op things.

Diffstat:
include/kore/python_methods.h | 2++
src/python.c | 27++++++++++++++++++++++++---
2 files changed, 26 insertions(+), 3 deletions(-)

diff --git a/include/kore/python_methods.h b/include/kore/python_methods.h @@ -518,6 +518,7 @@ struct pyproc { pid_t apid; int reaped; int status; + struct pyproc_op *op; struct pysocket *in; struct pysocket *out; struct python_coro *coro; @@ -563,6 +564,7 @@ static PyTypeObject pyproc_type = { struct pyproc_op { PyObject_HEAD struct pyproc *proc; + struct python_coro *coro; }; static void pyproc_op_dealloc(struct pyproc_op *); diff --git a/src/python.c b/src/python.c @@ -472,6 +472,7 @@ void kore_python_proc_reap(void) { struct pyproc *proc; + struct python_coro *coro; pid_t child; int status; @@ -507,10 +508,20 @@ kore_python_proc_reap(void) proc->timer = NULL; } - if (proc->coro->request != NULL) - http_request_wakeup(proc->coro->request); + /* + * If someone is waiting on proc.reap() then wakeup that + * coroutine, otherwise wakeup the coroutine that created + * the process. + */ + if (proc->op != NULL) + coro = proc->op->coro; + else + coro = proc->coro; + + if (coro->request != NULL) + http_request_wakeup(coro->request); else - python_coro_wakeup(proc->coro); + python_coro_wakeup(coro); } } @@ -2289,6 +2300,7 @@ python_kore_proc(PyObject *self, PyObject *args) } proc->pid = -1; + proc->op = NULL; proc->apid = -1; proc->reaped = 0; proc->status = 0; @@ -3721,6 +3733,12 @@ pyproc_reap(struct pyproc *proc, PyObject *args) { struct pyproc_op *op; + if (proc->op != NULL) { + PyErr_Format(PyExc_RuntimeError, + "process %d already being reaped", proc->apid); + return (NULL); + } + if (proc->timer != NULL) { kore_timer_remove(proc->timer); proc->timer = NULL; @@ -3730,6 +3748,9 @@ pyproc_reap(struct pyproc *proc, PyObject *args) return (NULL); op->proc = proc; + op->coro = coro_running; + + proc->op = op; Py_INCREF((PyObject *)proc);