diff --git a/kitty/child-monitor.c b/kitty/child-monitor.c index dfd070261..612c9f8cd 100644 --- a/kitty/child-monitor.c +++ b/kitty/child-monitor.c @@ -14,6 +14,7 @@ #undef _GNU_SOURCE #endif #include "data-types.h" +#include #include #include #include @@ -356,6 +357,38 @@ resize_pty(ChildMonitor *self, PyObject *args) { return found; } +bool +set_iutf8(int UNUSED fd, bool UNUSED on) { +#ifdef IUTF8 + struct termios attrs; + if (tcgetattr(fd, &attrs) != 0) return false; + if (on) attrs.c_iflag |= IUTF8; + else attrs.c_iflag &= ~IUTF8; + if (tcsetattr(fd, TCSANOW, &attrs) != 0) return false; +#endif + return true; +} + +static PyObject* +pyset_iutf8(ChildMonitor *self, PyObject *args) { + unsigned long window_id; + int on; + PyObject *found = Py_False; + if (!PyArg_ParseTuple(args, "kp", &window_id, &on)) return NULL; + children_mutex(lock); + for (size_t i = 0; i < self->count; i++) { + if (children[i].id == window_id) { + found = Py_True; + if (!set_iutf8(fds[EXTRA_FDS + i].fd, on & 1)) PyErr_SetFromErrno(PyExc_OSError); + break; + } + } + children_mutex(unlock); + if (PyErr_Occurred()) return NULL; + Py_INCREF(found); + return found; +} + #undef FREE_CHILD #undef INCREF_CHILD #undef DECREF_CHILD @@ -581,6 +614,7 @@ static PyMethodDef methods[] = { METHOD(main_loop, METH_NOARGS) METHOD(mark_for_close, METH_VARARGS) METHOD(resize_pty, METH_VARARGS) + {"set_iutf8", (PyCFunction)pyset_iutf8, METH_VARARGS, ""}, {NULL} /* Sentinel */ }; diff --git a/kitty/child.py b/kitty/child.py index bf1c16d83..76a2973c0 100644 --- a/kitty/child.py +++ b/kitty/child.py @@ -3,7 +3,6 @@ # License: GPL v3 Copyright: 2016, Kovid Goyal import os -import termios import fcntl import signal from threading import Thread @@ -33,7 +32,7 @@ class Child: self.forked = True master, slave = os.openpty() # Note that master and slave are in blocking mode remove_cloexec(slave) - self.set_iutf8(fd=master) + fast_data_types.set_iutf8(master, True) stdin, self.stdin = self.stdin, None if stdin is not None: stdin_read_fd, stdin_write_fd = os.pipe() @@ -76,16 +75,6 @@ class Child: t.start() return pid - def set_iutf8(self, on=True, fd=None): - fd = fd or self.child_fd - if fd is not None and hasattr(fast_data_types, 'IUTF8'): - attrs = termios.tcgetattr(fd) - if on: - attrs[0] |= fast_data_types.IUTF8 - else: - attrs[0] &= ~fast_data_types.IUTF8 - termios.tcsetattr(fd, termios.TCSANOW, attrs) - def hangup(self): if self.pid is not None: pid, self.pid = self.pid, None diff --git a/kitty/data-types.c b/kitty/data-types.c index 37f301dd4..e3c946bb2 100644 --- a/kitty/data-types.c +++ b/kitty/data-types.c @@ -37,6 +37,14 @@ redirect_std_streams(PyObject UNUSED *self, PyObject *args) { Py_RETURN_NONE; } +static PyObject* +pyset_iutf8(PyObject UNUSED *self, PyObject *args) { + int fd, on; + if (!PyArg_ParseTuple(args, "ip", &fd, &on)) return NULL; + if (!set_iutf8(fd, on & 1)) return PyErr_SetFromErrno(PyExc_OSError); + Py_RETURN_NONE; +} + #ifdef WITH_PROFILER static PyObject* start_profiler(PyObject UNUSED *self, PyObject *args) { @@ -59,6 +67,7 @@ stop_profiler(PyObject UNUSED *self) { static PyMethodDef module_methods[] = { GL_METHODS + {"set_iutf8", (PyCFunction)pyset_iutf8, METH_VARARGS, ""}, {"parse_bytes", (PyCFunction)parse_bytes, METH_VARARGS, ""}, {"parse_bytes_dump", (PyCFunction)parse_bytes_dump, METH_VARARGS, ""}, {"redirect_std_streams", (PyCFunction)redirect_std_streams, METH_VARARGS, ""}, @@ -144,9 +153,6 @@ PyInit_fast_data_types(void) { PyModule_AddIntMacro(m, NORMAL_PROTOCOL); PyModule_AddIntMacro(m, URXVT_PROTOCOL); PyModule_AddIntMacro(m, UTF8_PROTOCOL); -#ifdef IUTF8 - PyModule_AddIntMacro(m, IUTF8); -#endif } return m; diff --git a/kitty/data-types.h b/kitty/data-types.h index 626644912..f47720cef 100644 --- a/kitty/data-types.h +++ b/kitty/data-types.h @@ -355,6 +355,7 @@ double timers_timeout(Timers*); void timers_call(Timers*); bool timers_add(Timers *self, double delay, bool, PyObject *callback, PyObject *args); bool timers_add_if_missing(Timers *self, double delay, PyObject *callback, PyObject *args); +bool set_iutf8(int, bool); color_type colorprofile_to_color(ColorProfile *self, color_type entry, color_type defval); diff --git a/kitty/window.py b/kitty/window.py index 664db4eaf..e72bb5def 100644 --- a/kitty/window.py +++ b/kitty/window.py @@ -130,7 +130,7 @@ class Window: glfw_post_empty_event() def use_utf8(self, on): - self.child.set_iutf8(on) + get_boss().child_monitor.set_iutf8(self.window_id, on) def update_screen(self): self.char_grid.update_cell_data()