/* arch-tag: 5f35327e-caf3-4ada-9109-a52b45684949 */ #include #include #include #include #include "unix.h" #include "pty-outfifo.h" #include "resizeable_buf.h" #include "panic.h" #include "unicode.h" struct pty *pty; GIOChannel *pty_channel; GMainLoop *mainloop; static fifo_t out_fifo = FIFO_BLANK; static gboolean on_writeable(GIOChannel *source, GIOCondition event, void *_null) { ssize_t n2; size_t n = FIFO_LEN(out_fifo); int fd = g_io_channel_unix_get_fd(source); //fprintf(stderr, "on_writeable %u\n", n); if(n) { if((n2 = write(fd, FIFO_PTR(out_fifo), n)) < 0) { if(errno == EINTR) return TRUE; else panicno("on_writeable, write"); } if (n2 < n) { FIFO_POP(out_fifo, n2); //fprintf(stderr, "on_writeable wait %u\n", n - n2); assert(!FIFO_EMPTY(out_fifo)); return TRUE; } FIFO_CLEAR(out_fifo); } assert(FIFO_EMPTY(out_fifo)); return false; } void stuff_buf(struct pty *pty, char *buf, int len) { if(!len) return; if(FIFO_EMPTY(out_fifo)) { if(!pty_channel) pty_channel = g_io_channel_unix_new(pty->fd); g_io_add_watch(pty_channel, G_IO_OUT, on_writeable, NULL); } fifo_append(&out_fifo, buf, len); } void send_string(struct pty *pty, char *s) { stuff_buf(pty, s, strlen(s)); } void send_wchar(struct pty * pty, wchar_t ch) { char buf[8]; int n = utf8_wctomb(buf,ch,8); assert(n > 0); stuff_buf(pty, buf, n); }