1 /*- 2 * Copyright (c) 1983, 1985 3 * The Regents of the University of California. All rights reserved. 4 * 5 * %sccs.include.redist.c% 6 */ 7 8 #ifndef lint 9 static char sccsid[] = "@(#)io.c 5.1 (Berkeley) 6/6/85"; 10 #endif not lint 11 12 /* 13 * This file contains the I/O handling and the exchange of 14 * edit characters. This connection itself is established in 15 * ctl.c 16 */ 17 18 #include "talk.h" 19 #include <sys/ioctl.h> 20 #include <sys/time.h> 21 #include <errno.h> 22 #include <stdio.h> 23 #include <string.h> 24 #include <unistd.h> 25 26 #define A_LONG_TIME 10000000 27 #define STDIN_MASK (1<<fileno(stdin)) /* the bit mask for standard 28 input */ 29 extern int errno; 30 31 /* 32 * The routine to do the actual talking 33 */ 34 void 35 talk() 36 { 37 register int read_template, sockt_mask; 38 int read_set, nb; 39 char buf[BUFSIZ]; 40 struct timeval wait; 41 42 message("Connection established\007\007\007"); 43 current_line = 0; 44 sockt_mask = (1<<sockt); 45 46 /* 47 * Wait on both the other process (sockt_mask) and 48 * standard input ( STDIN_MASK ) 49 */ 50 read_template = sockt_mask | STDIN_MASK; 51 forever { 52 read_set = read_template; 53 wait.tv_sec = A_LONG_TIME; 54 wait.tv_usec = 0; 55 nb = select(32, (fd_set *)&read_set, 0, 0, &wait); 56 if (nb <= 0) { 57 if (errno == EINTR) { 58 read_set = read_template; 59 continue; 60 } 61 /* panic, we don't know what happened */ 62 p_error("Unexpected error from select"); 63 quit(); 64 } 65 if (read_set & sockt_mask) { 66 /* There is data on sockt */ 67 nb = read(sockt, buf, sizeof buf); 68 if (nb <= 0) { 69 message("Connection closed. Exiting"); 70 quit(); 71 } 72 display(&his_win, buf, nb); 73 } 74 if (read_set & STDIN_MASK) { 75 /* 76 * We can't make the tty non_blocking, because 77 * curses's output routines would screw up 78 */ 79 ioctl(0, FIONREAD, (struct sgttyb *) &nb); 80 nb = read(0, buf, nb); 81 display(&my_win, buf, nb); 82 /* might lose data here because sockt is non-blocking */ 83 write(sockt, buf, nb); 84 } 85 } 86 } 87 88 extern int errno; 89 90 /* 91 * p_error prints the system error message on the standard location 92 * on the screen and then exits. (i.e. a curses version of perror) 93 */ 94 __dead void 95 p_error(string) 96 const char *string; 97 { 98 char *sys; 99 100 sys = strerror(errno); 101 wmove(my_win.x_win, current_line%my_win.x_nlines, 0); 102 wprintw(my_win.x_win, "[%s : %s (%d)]\n", string, sys, errno); 103 wrefresh(my_win.x_win); 104 move(LINES-1, 0); 105 refresh(); 106 quit(); 107 } 108 109 /* 110 * Display string in the standard location 111 */ 112 void 113 message(string) 114 const char *string; 115 { 116 117 wmove(my_win.x_win, current_line%my_win.x_nlines, 0); 118 wprintw(my_win.x_win, "[%s]\n", string); 119 wrefresh(my_win.x_win); 120 } 121