132147Sminshall /* 232147Sminshall * The following routines try to encapsulate what is system dependent 332147Sminshall * (at least between 4.x and dos) which is used in telnet.c. 432147Sminshall */ 532147Sminshall 632147Sminshall #if defined(unix) 732147Sminshall 832147Sminshall #include <sys/ioctl.h> 932147Sminshall #include <sys/time.h> 1032147Sminshall #include <signal.h> 1132147Sminshall 1232147Sminshall #include "defines.h" 1332147Sminshall #include "externs.h" 1432147Sminshall #include "types.h" 1532147Sminshall 1632147Sminshall int 1732147Sminshall HaveInput; /* There is input available to scan */ 1832147Sminshall 1932147Sminshall #if defined(TN3270) 2032147Sminshall static char tline[200]; 2132147Sminshall char *transcom = 0; /* transparent mode command (default: none) */ 2232147Sminshall #endif /* defined(TN3270) */ 2332147Sminshall 2432147Sminshall static struct tchars otc = { 0 }, ntc = { 0 }; 2532147Sminshall static struct ltchars oltc = { 0 }, nltc = { 0 }; 2632147Sminshall static struct sgttyb ottyb = { 0 }, nttyb = { 0 }; 2732147Sminshall 2832147Sminshall 2932147Sminshall TerminalWrite(fd, buf, n) 3032147Sminshall int fd; 3132147Sminshall char *buf; 3232147Sminshall int n; 3332147Sminshall { 3432147Sminshall return write(fd, buf, n); 3532147Sminshall } 3632147Sminshall 3732147Sminshall TerminalRead(fd, buf, n) 3832147Sminshall int fd; 3932147Sminshall char *buf; 4032147Sminshall int n; 4132147Sminshall { 4232147Sminshall return read(fd, buf, n); 4332147Sminshall } 4432147Sminshall 4532147Sminshall /* 4632147Sminshall * 4732147Sminshall */ 4832147Sminshall 4932147Sminshall int 5032147Sminshall TerminalAutoFlush() /* unix */ 5132147Sminshall { 5232147Sminshall #if defined(LNOFLSH) 5332147Sminshall int flush; 5432147Sminshall 5532147Sminshall ioctl(0, TIOCLGET, (char *)&flush); 5632147Sminshall return !(flush&LNOFLSH); /* if LNOFLSH, no autoflush */ 5732147Sminshall #else /* LNOFLSH */ 5832147Sminshall return 1; 5932147Sminshall #endif /* LNOFLSH */ 6032147Sminshall } 6132147Sminshall 6232147Sminshall /* 6332147Sminshall * TerminalSpecialChars() 6432147Sminshall * 6532147Sminshall * Look at an input character to see if it is a special character 6632147Sminshall * and decide what to do. 6732147Sminshall * 6832147Sminshall * Output: 6932147Sminshall * 7032147Sminshall * 0 Don't add this character. 7132147Sminshall * 1 Do add this character 7232147Sminshall */ 7332147Sminshall 7432147Sminshall int 7532147Sminshall TerminalSpecialChars(c) /* unix */ 7632147Sminshall int c; 7732147Sminshall { 7832147Sminshall void doflush(), intp(), sendbrk(); 7932147Sminshall 8032147Sminshall if (c == ntc.t_intrc) { 8132147Sminshall intp(); 8232147Sminshall return 0; 8332147Sminshall } else if (c == ntc.t_quitc) { 8432147Sminshall sendbrk(); 8532147Sminshall return 0; 8632147Sminshall } else if (c == nltc.t_flushc) { 8732147Sminshall xmitAO(); /* Transmit Abort Output */ 8832147Sminshall return 0; 8932147Sminshall } else if (!MODE_LOCAL_CHARS(globalmode)) { 9032147Sminshall if (c == nttyb.sg_kill) { 9132147Sminshall xmitEL(); 9232147Sminshall return 0; 9332147Sminshall } else if (c == nttyb.sg_erase) { 9432147Sminshall xmitEC(); /* Transmit Erase Character */ 9532147Sminshall return 0; 9632147Sminshall } 9732147Sminshall } 9832147Sminshall return 1; 9932147Sminshall } 10032147Sminshall 10132147Sminshall 10232147Sminshall /* 10332147Sminshall * Flush output to the terminal 10432147Sminshall */ 10532147Sminshall 10632147Sminshall void 10732147Sminshall TerminalFlushOutput() /* unix */ 10832147Sminshall { 10932147Sminshall (void) ioctl(fileno(stdout), TIOCFLUSH, (char *) 0); 11032147Sminshall } 11132147Sminshall 11232147Sminshall void 11332147Sminshall TerminalSaveState() /* unix */ 11432147Sminshall { 11532147Sminshall ioctl(0, TIOCGETP, (char *)&ottyb); 11632147Sminshall ioctl(0, TIOCGETC, (char *)&otc); 11732147Sminshall ioctl(0, TIOCGLTC, (char *)&oltc); 11832147Sminshall 11932147Sminshall ntc = otc; 12032147Sminshall nltc = oltc; 12132147Sminshall nttyb = ottyb; 122*32254Sminshall 123*32254Sminshall termEofChar = ntc.t_eofc; 124*32254Sminshall termEraseChar = nttyb.sg_erase; 125*32254Sminshall termFlushChar = nltc.t_flushc; 126*32254Sminshall termIntChar = ntc.t_intrc; 127*32254Sminshall termKillChar = nttyb.sg_kill; 128*32254Sminshall termQuitChar = ntc.t_quitc; 12932147Sminshall } 13032147Sminshall 13132147Sminshall void 13232147Sminshall TerminalRestoreState() /* unix */ 13332147Sminshall { 13432147Sminshall } 13532147Sminshall 13632147Sminshall /* 13732147Sminshall * TerminalNewMode - set up terminal to a specific mode. 13832147Sminshall */ 13932147Sminshall 14032147Sminshall 14132147Sminshall void 14232147Sminshall TerminalNewMode(fd_in, fd_out, f) /* unix */ 14332147Sminshall int fd_in, fd_out; /* File descriptor */ 14432147Sminshall register int f; 14532147Sminshall { 14632147Sminshall static int prevmode = 0; 14732147Sminshall struct tchars *tc; 14832147Sminshall struct tchars tc3; 14932147Sminshall struct ltchars *ltc; 15032147Sminshall struct sgttyb sb; 15132147Sminshall int onoff; 15232147Sminshall int old; 15332147Sminshall struct tchars notc2; 15432147Sminshall struct ltchars noltc2; 15532147Sminshall static struct tchars notc = { -1, -1, -1, -1, -1, -1 }; 15632147Sminshall static struct ltchars noltc = { -1, -1, -1, -1, -1, -1 }; 15732147Sminshall 15832147Sminshall globalmode = f; 15932147Sminshall if (prevmode == f) 16032147Sminshall return; 16132147Sminshall old = prevmode; 16232147Sminshall prevmode = f; 16332147Sminshall sb = nttyb; 16432147Sminshall 16532147Sminshall switch (f) { 16632147Sminshall 16732147Sminshall case 0: 16832147Sminshall onoff = 0; 16932147Sminshall tc = &otc; 17032147Sminshall ltc = &oltc; 17132147Sminshall break; 17232147Sminshall 17332147Sminshall case 1: /* remote character processing, remote echo */ 17432147Sminshall case 2: /* remote character processing, local echo */ 17532147Sminshall case 6: /* 3270 mode - like 1, but with xon/xoff local */ 17632147Sminshall /* (might be nice to have "6" in telnet also...) */ 17732147Sminshall sb.sg_flags |= CBREAK; 17832147Sminshall if ((f == 1) || (f == 6)) { 17932147Sminshall sb.sg_flags &= ~(ECHO|CRMOD); 18032147Sminshall } else { 18132147Sminshall sb.sg_flags |= ECHO|CRMOD; 18232147Sminshall } 18332147Sminshall sb.sg_erase = sb.sg_kill = -1; 18432147Sminshall if (f == 6) { 18532147Sminshall tc = &tc3; 18632147Sminshall tc3 = notc; 18732147Sminshall /* get XON, XOFF characters */ 18832147Sminshall tc3.t_startc = otc.t_startc; 18932147Sminshall tc3.t_stopc = otc.t_stopc; 19032147Sminshall } else { 19132147Sminshall /* 19232147Sminshall * If user hasn't specified one way or the other, 19332147Sminshall * then default to not trapping signals. 19432147Sminshall */ 19532147Sminshall if (!donelclchars) { 19632147Sminshall localchars = 0; 19732147Sminshall } 19832147Sminshall if (localchars) { 19932147Sminshall notc2 = notc; 20032147Sminshall notc2.t_intrc = ntc.t_intrc; 20132147Sminshall notc2.t_quitc = ntc.t_quitc; 20232147Sminshall tc = ¬c2; 20332147Sminshall } else { 20432147Sminshall tc = ¬c; 20532147Sminshall } 20632147Sminshall } 20732147Sminshall ltc = &noltc; 20832147Sminshall onoff = 1; 20932147Sminshall break; 21032147Sminshall case 3: /* local character processing, remote echo */ 21132147Sminshall case 4: /* local character processing, local echo */ 21232147Sminshall case 5: /* local character processing, no echo */ 21332147Sminshall sb.sg_flags &= ~CBREAK; 21432147Sminshall sb.sg_flags |= CRMOD; 21532147Sminshall if (f == 4) 21632147Sminshall sb.sg_flags |= ECHO; 21732147Sminshall else 21832147Sminshall sb.sg_flags &= ~ECHO; 21932147Sminshall notc2 = ntc; 22032147Sminshall tc = ¬c2; 22132147Sminshall noltc2 = oltc; 22232147Sminshall ltc = &noltc2; 22332147Sminshall /* 22432147Sminshall * If user hasn't specified one way or the other, 22532147Sminshall * then default to trapping signals. 22632147Sminshall */ 22732147Sminshall if (!donelclchars) { 22832147Sminshall localchars = 1; 22932147Sminshall } 23032147Sminshall if (localchars) { 23132147Sminshall notc2.t_brkc = nltc.t_flushc; 23232147Sminshall noltc2.t_flushc = -1; 23332147Sminshall } else { 23432147Sminshall notc2.t_intrc = notc2.t_quitc = -1; 23532147Sminshall } 23632147Sminshall noltc2.t_suspc = escape; 23732147Sminshall noltc2.t_dsuspc = -1; 23832147Sminshall onoff = 1; 23932147Sminshall break; 24032147Sminshall 24132147Sminshall default: 24232147Sminshall return; 24332147Sminshall } 24432147Sminshall ioctl(fd_in, TIOCSLTC, (char *)ltc); 24532147Sminshall ioctl(fd_in, TIOCSETC, (char *)tc); 24632147Sminshall ioctl(fd_in, TIOCSETP, (char *)&sb); 24732147Sminshall #if (!defined(TN3270)) || ((!defined(NOT43)) || defined(PUTCHAR)) 24832147Sminshall ioctl(fd_in, FIONBIO, (char *)&onoff); 24932147Sminshall ioctl(fd_out, FIONBIO, (char *)&onoff); 25032147Sminshall #endif /* (!defined(TN3270)) || ((!defined(NOT43)) || defined(PUTCHAR)) */ 25132147Sminshall #if defined(TN3270) 25232147Sminshall if (noasynch == 0) { 25332147Sminshall ioctl(fd_in, FIOASYNC, (char *)&onoff); 25432147Sminshall } 25532147Sminshall #endif /* defined(TN3270) */ 25632147Sminshall 25732147Sminshall if (MODE_LINE(f)) { 25832147Sminshall void doescape(); 25932147Sminshall 26032147Sminshall signal(SIGTSTP, doescape); 26132147Sminshall } else if (MODE_LINE(old)) { 26232147Sminshall signal(SIGTSTP, SIG_DFL); 26332147Sminshall sigsetmask(sigblock(0) & ~(1<<(SIGTSTP-1))); 26432147Sminshall } 26532147Sminshall } 26632147Sminshall 26732147Sminshall 26832147Sminshall int 26932147Sminshall NetClose(net) 27032147Sminshall int net; 27132147Sminshall { 27232147Sminshall return close(net); 27332147Sminshall } 27432147Sminshall 27532147Sminshall 27632147Sminshall void 27732147Sminshall NetNonblockingIO(fd, onoff) /* unix */ 27832147Sminshall int 27932147Sminshall fd, 28032147Sminshall onoff; 28132147Sminshall { 28232147Sminshall ioctl(fd, FIONBIO, (char *)&onoff); 28332147Sminshall } 28432147Sminshall 28532147Sminshall void 28632147Sminshall NetSigIO(fd, onoff) /* unix */ 28732147Sminshall int 28832147Sminshall fd, 28932147Sminshall onoff; 29032147Sminshall { 29132147Sminshall ioctl(fd, FIOASYNC, (char *)&onoff); /* hear about input */ 29232147Sminshall } 29332147Sminshall 29432147Sminshall void 29532147Sminshall NetSetPgrp(fd) /* unix */ 29632147Sminshall int fd; 29732147Sminshall { 29832147Sminshall int myPid; 29932147Sminshall 30032147Sminshall myPid = getpid(); 30132147Sminshall #if defined(NOT43) 30232147Sminshall myPid = -myPid; 30332147Sminshall #endif /* defined(NOT43) */ 30432147Sminshall ioctl(fd, SIOCSPGRP, (char *)&myPid); /* set my pid */ 30532147Sminshall } 30632147Sminshall 30732147Sminshall 30832147Sminshall #endif /* defined(unix) */ 309