X-Git-Url: https://www.chiark.greenend.org.uk/ucgi/~ianmdlvl/git?a=blobdiff_plain;f=src%2Fterminal.c;h=9a3290eeee645e81057f6e326ce84ceaa732b8a3;hb=1191192d054da2be10658472c29f95e2494ea18f;hp=a4cd31b4fde6209a2182ee48cf36129ed255409e;hpb=b1a35823c1660150770c939fb378e93b4f3066b1;p=sympathy.git diff --git a/src/terminal.c b/src/terminal.c index a4cd31b..9a3290e 100644 --- a/src/terminal.c +++ b/src/terminal.c @@ -10,6 +10,30 @@ static char rcsid[] = "$Id$"; /* * $Log$ + * Revision 1.9 2008/02/15 03:32:07 james + * *** empty log message *** + * + * Revision 1.8 2008/02/14 10:39:14 james + * *** empty log message *** + * + * Revision 1.7 2008/02/14 01:55:57 james + * *** empty log message *** + * + * Revision 1.6 2008/02/14 00:57:58 james + * *** empty log message *** + * + * Revision 1.5 2008/02/13 18:05:06 james + * *** empty log message *** + * + * Revision 1.4 2008/02/13 16:57:29 james + * *** empty log message *** + * + * Revision 1.3 2008/02/13 09:12:21 james + * *** empty log message *** + * + * Revision 1.2 2008/02/13 01:08:18 james + * *** empty log message *** + * * Revision 1.1 2008/02/12 22:36:46 james * *** empty log message *** * @@ -44,33 +68,107 @@ typedef struct TERMINAL_struct } TERMINAL; -static TERMINAL terminal_list=NULL; +static TERMINAL *terminal_list = NULL; +int terminal_winches; + static void terminal_close (TTY * _t) { + char buf[32]; + int i; + TERMINAL *t = (TERMINAL *) _t; - TERMINAL **ptr=&terminal_list; + TERMINAL **ptr = &terminal_list; if (!t) return; /* Take out of cleanup list */ - while (*ptr && (*ptr != t)) ptr=&((*ptr)->next); + while (*ptr && (*ptr != t)) + ptr = &((*ptr)->next); - if (*ptr) - *ptr=t->next; + if (*ptr) + *ptr = t->next; - tcsetattr(t->wfd,TCSANOW,&t->orig_termios); + tcsetattr (t->wfd, TCSANOW, &t->orig_termios); - set_blocking(t->rfd); - set_blocking(t->wfd); + set_nonblocking (t->wfd); + + + t->xmit (_t, "\033[r", 3); + t->xmit (_t, "\033[0m", 4); + i = sprintf (buf, "\033[%d;%dH", CRT_ROWS + 1, 1); + t->xmit (_t, buf, i); + t->xmit (_t, "\033[J", 3); + + set_blocking (t->rfd); + set_blocking (t->wfd); free (t); } +void +terminal_atexit (void) +{ + while (terminal_list) + terminal_close ((TTY *) terminal_list); +} + +static void +sigint (int dummy) +{ + terminal_atexit (); + exit (-1); +} + +static void +sigwinch (int not) +{ + terminal_winches++; +} + + +void +terminal_getsize (TTY * _t) +{ + TERMINAL *t = (TERMINAL *) _t; + struct winsize sz = { 0 }; + + if (!t) + return; + + if (ioctl (t->wfd, TIOCGWINSZ, &sz)) + { + t->size.x = CRT_COLS; + t->size.y = CRT_ROWS; + } + else + { + t->size.x = sz.ws_col; + t->size.y = sz.ws_row; + } +} + + +void +terminal_dispatch (void) +{ + TERMINAL *t; + + + if (!terminal_winches) + return; + + terminal_winches = 0; + + for (t = terminal_list; t; t = t->next) + terminal_getsize ((TTY *) t); + +} + static int terminal_read (TTY * _t, void *buf, int len) @@ -78,10 +176,13 @@ terminal_read (TTY * _t, void *buf, int len) TERMINAL *t = (TERMINAL *) _t; int red, done = 0; + terminal_dispatch (); + set_nonblocking (t->rfd); + do { - red = wrap_read (t->fd, buf, len); + red = wrap_read (t->rfd, buf, len); if (red < 0) return -1; if (!red) @@ -104,14 +205,19 @@ terminal_write (TTY * _t, void *buf, int len) int writ, done = 0; TERMINAL *t = (TERMINAL *) _t; + terminal_dispatch (); + + set_blocking (t->wfd); + do { - writ = wrap_write (t->fd, buf, len); + writ = wrap_write (t->wfd, buf, len); if (writ < 0) return -1; + if (!writ) - sleep (1); + usleep (1000); buf += writ; len -= writ; @@ -123,67 +229,58 @@ terminal_write (TTY * _t, void *buf, int len) return done; } + +void +terminal_register_handlers (void) +{ + struct sigaction sa = { 0 }; + + sa.sa_handler = sigwinch; + sa.sa_flags = SA_RESTART; + sigaction (SIGWINCH, &sa, NULL); + + sa.sa_handler = sigint; + sa.sa_flags = SA_RESTART; + sigaction (SIGINT, &sa, NULL); +} + + TTY * -terminal_open (int rfd,int wfd) +terminal_open (int rfd, int wfd) { TERMINAL *t; pid_t child; - char name[1024]; struct termios termios; t = (TERMINAL *) malloc (sizeof (TERMINAL)); + strcpy (t->name, "terminal"); t->rfd = rfd; t->wfd = wfd; - tcgetattr(wfd,&t->orig_termios); + tcgetattr (wfd, &t->orig_termios); - t->next=terminal_list; - terminal_list=t; + t->next = terminal_list; + terminal_list = t; - tcgetattr(tfd,&termios); + tcgetattr (wfd, &termios); set_nonblocking (rfd); set_nonblocking (wfd); - raw_termios (&termios); + cfmakeraw (&termios); + //raw_termios (&termios); - tcsetattr(wfd,TCSANOW,&termios); + tcsetattr (wfd, TCSANOW, &termios); - t->read = terminal_read; - t->write = terminal_write; + t->recv = terminal_read; + t->xmit = terminal_write; t->close = terminal_close; + t->blocked = 0; - return (TTY *) t; -} - -void -terminal_getsize (TTY *_t,CRT_POS *pos) -{ -TERMINAL *t=(TTY *) _t; - struct winsize sz = { 0 }; - -if ((!t) || (!pos)) return; + terminal_getsize ((TTY *) t); -if (ioctl (a->wfd, TIOCGWINSZ, &sz)) - { - pos->x = CRT_COLS; - pos->y = CRT_ROWS; - } - else - { - pos->x = sz.ws_col; - pos->y = sz.ws_row; - } -} - - -void terminal_atexit(void) -{ -while (terminal_list) - terminal_close(terminal_list); + return (TTY *) t; } - -