mirror of
https://github.com/rizinorg/cutter.git
synced 2025-02-20 21:56:06 +00:00
Fix IPyKernel restarting
This commit is contained in:
parent
06dffde0fe
commit
b45314fd19
@ -3,6 +3,7 @@ import logging
|
||||
import threading
|
||||
import signal
|
||||
import cutter_internal
|
||||
import zmq
|
||||
from ipykernel.kernelapp import IPKernelApp
|
||||
from ipykernel.ipkernel import IPythonKernel
|
||||
|
||||
@ -28,6 +29,16 @@ class IPyKernelInterfaceKernel:
|
||||
else:
|
||||
return 0
|
||||
|
||||
def cleanup(self):
|
||||
self._app.heartbeat.context.destroy()
|
||||
self._thread.join()
|
||||
self._app.heartbeat.join()
|
||||
self._app.iopub_thread.stop()
|
||||
self._app.kernel.shell.history_manager.save_thread.stop()
|
||||
zmq.Context.instance().destroy()
|
||||
# successful if only the main thread remains
|
||||
return len(threading.enumerate()) == 1
|
||||
|
||||
|
||||
class CutterIPythonKernel(IPythonKernel):
|
||||
def __init__(self, **kwargs):
|
||||
@ -59,7 +70,7 @@ def launch_ipykernel(argv):
|
||||
|
||||
def run_kernel():
|
||||
app.kernel_class = CutterIPythonKernel
|
||||
#app.log_level = logging.DEBUG
|
||||
# app.log_level = logging.DEBUG
|
||||
app.initialize(argv[3:])
|
||||
app.start()
|
||||
|
||||
|
@ -156,3 +156,29 @@ NestedIPyKernel *JupyterConnection::getNestedIPyKernel(long id)
|
||||
}
|
||||
return *it;
|
||||
}
|
||||
|
||||
QVariant JupyterConnection::pollNestedIPyKernel(long id)
|
||||
{
|
||||
auto it = kernels.find(id);
|
||||
if(it == kernels.end())
|
||||
{
|
||||
return QVariant(0);
|
||||
}
|
||||
|
||||
NestedIPyKernel *kernel = *it;
|
||||
QVariant v = kernel->poll();
|
||||
|
||||
if(!v.isNull())
|
||||
{
|
||||
// if poll of kernel returns anything but None, it has already quit and should be cleaned up
|
||||
PyThreadState *subinterpreterState = kernel->getThreadState();
|
||||
delete kernel;
|
||||
kernels.erase(it);
|
||||
|
||||
PyThreadState *parentThreadState = PyThreadState_Swap(subinterpreterState);
|
||||
Py_EndInterpreter(subinterpreterState);
|
||||
PyThreadState_Swap(parentThreadState);
|
||||
}
|
||||
|
||||
return v;
|
||||
}
|
||||
|
@ -26,6 +26,7 @@ public:
|
||||
|
||||
long startNestedIPyKernel(const QStringList &argv);
|
||||
NestedIPyKernel *getNestedIPyKernel(long id);
|
||||
QVariant pollNestedIPyKernel(long id);
|
||||
|
||||
signals:
|
||||
void urlReceived(const QString &url);
|
||||
|
@ -62,6 +62,13 @@ NestedIPyKernel::NestedIPyKernel(PyObject *cutterIPykernelModule, const QStringL
|
||||
|
||||
NestedIPyKernel::~NestedIPyKernel()
|
||||
{
|
||||
auto parentThreadState = PyThreadState_Swap(threadState);
|
||||
auto ret = PyObject_CallMethod(kernel, "cleanup", nullptr);
|
||||
if (!ret)
|
||||
{
|
||||
PyErr_Print();
|
||||
}
|
||||
PyThreadState_Swap(parentThreadState);
|
||||
}
|
||||
|
||||
void NestedIPyKernel::sendSignal(long signum)
|
||||
|
@ -20,6 +20,8 @@ public:
|
||||
void sendSignal(long signum);
|
||||
QVariant poll();
|
||||
|
||||
PyThreadState *getThreadState() { return threadState; }
|
||||
|
||||
private:
|
||||
NestedIPyKernel(PyObject *cutterIPykernelModule, const QStringList &argv);
|
||||
|
||||
|
@ -110,13 +110,7 @@ PyObject *api_internal_kernel_interface_poll(PyObject *, PyObject *args)
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
NestedIPyKernel *kernel = Jupyter()->getNestedIPyKernel(id);
|
||||
if(!kernel)
|
||||
{
|
||||
return PyLong_FromLong(0);
|
||||
}
|
||||
|
||||
QVariant v = kernel->poll();
|
||||
QVariant v = Jupyter()->pollNestedIPyKernel(id);
|
||||
bool ok;
|
||||
auto ret = static_cast<long>(v.toLongLong(&ok));
|
||||
if(ok)
|
||||
|
Loading…
Reference in New Issue
Block a user