📄 sysdep1.c
字号:
/* * sysdep1.c system dependant routines. * * m_dtrtoggle - dropt dtr and raise it again * m_break - send BREAK signal * m_getdcd - get modem dcd status * m_setdcd - set modem dcd status * m_savestate - save modem state * m_restorestate - restore saved modem state * m_nohang - tell driver not to hang up at DTR drop * m_hupcl - set hangup on close on/off * m_setparms - set speed, parity, bits and stopbits * m_readchk - see if there is input waiting. * m_wait - wait for child to finish. Sysdep. too. * * If it's possible, Posix termios are preferred. * * This file is part of the minicom communications package, * Copyright 1991-1995 Miquel van Smoorenburg. * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation; either version * 2 of the License, or (at your option) any later version. * * jl 23.06.97 adjustable DTR downtime */#ifdef HAVE_CONFIG_H#include <config.h>#endif#include "rcsid.h"RCSID("$Id: sysdep1.c,v 1.6 2000/06/24 16:01:29 walker Exp $")#include "sysdep.h"/* Set hardware flow control. */void m_sethwf(fd, on)int fd, on;{#ifdef _DGUX_SOURCE struct termiox x;#endif#ifdef POSIX_TERMIOS struct termios tty; tcgetattr(fd, &tty); if (on) tty.c_cflag |= CRTSCTS; else tty.c_cflag &= ~CRTSCTS; tcsetattr(fd, TCSANOW, &tty);#endif#ifdef _DGUX_SOURCE if (ioctl(fd, TCGETX, &x) < 0) { fprintf(stderr, _("can't get termiox attr.\n")); return; } x.x_hflag = on ? RTSXOFF|CTSXON : 0; if (ioctl(fd, TCSETX, &x) < 0) { fprintf(stderr, _("can't set termiox attr.\n")); return; }#endif}/* Set RTS line. Sometimes dropped. Linux specific? */void m_setrts(fd)int fd;{#if defined(TIOCM_RTS) && defined(TIOCMODG) int mcs=0; ioctl(fd, TIOCMODG, &mcs); mcs |= TIOCM_RTS; ioctl(fd, TIOCMODS, &mcs);#endif#ifdef _COHERENT ioctl(fd, TIOCSRTS, 0);#endif}/* * Drop DTR line and raise it again. */void m_dtrtoggle(fd,sec) int fd;int sec;{#ifdef TIOCSDTR /* Use the ioctls meant for this type of thing. */ ioctl(fd, TIOCCDTR, 0); if (sec>0) { sleep(sec); ioctl(fd, TIOCSDTR, 0); }#else /* TIOCSDTR */# if defined (POSIX_TERMIOS) && !defined(_HPUX_SOURCE) /* Posix - set baudrate to 0 and back */ struct termios tty, old; tcgetattr(fd, &tty); tcgetattr(fd, &old); cfsetospeed(&tty, B0); cfsetispeed(&tty, B0); tcsetattr(fd, TCSANOW, &tty); if (sec>0) { sleep(sec); tcsetattr(fd, TCSANOW, &old); }# else /* POSIX */# ifdef _V7 /* Just drop speed to 0 and back to normal again */ struct sgttyb sg, ng; ioctl(fd, TIOCGETP, &sg); ioctl(fd, TIOCGETP, &ng); ng.sg_ispeed = ng.sg_ospeed = 0; ioctl(fd, TIOCSETP, &ng); if (sec>0) { sleep(sec); ioctl(fd, TIOCSETP, &sg); }# endif /* _V7 */# ifdef _HPUX_SOURCE unsigned long mflag = 0L; ioctl(fd, MCSETAF, &mflag); ioctl(fd, MCGETA, &mflag); mflag = MRTS | MDTR; if (sec>0) { sleep(sec); ioctl(fd, MCSETAF, &mflag); }# endif /* _HPUX_SOURCE */# endif /* POSIX */#endif /* TIOCSDTR */}/* * Send a break */void m_break(fd)int fd;{ #ifdef POSIX_TERMIOS tcsendbreak(fd, 0);#else# ifdef _V7# ifndef TIOCSBRK struct sgttyb sg, ng; ioctl(fd, TIOCGETP, &sg); ioctl(fd, TIOCGETP, &ng); ng.sg_ispeed = ng.sg_ospeed = B110; ng.sg_flags = BITS8 | RAW; ioctl(fd, TIOCSETP, &ng); write(fd, "\0\0\0\0\0\0\0\0\0\0", 10); ioctl(fd, TIOCSETP, &sg);# else ioctl(fd, TIOCSBRK, 0); sleep(1); ioctl(fd, TIOCCBRK, 0);# endif# endif#endif}/* * Get the dcd status */int m_getdcd(fd)int fd;{#ifdef TIOCMODG int mcs=0; ioctl(fd, TIOCMODG, &mcs); return(mcs & TIOCM_CAR ? 1 : 0);#else (void)fd; return(0); /* Impossible!! (eg. Coherent) */#endif}/* Variables to save states in */#ifdef POSIX_TERMIOSstatic struct termios savetty;static int m_word;#else# if defined (_BSD43) || defined (_V7)static struct sgttyb sg;static struct tchars tch;static int lsw;static int m_word;# endif#endif/* * Save the state of a port */void m_savestate(fd)int fd;{#ifdef POSIX_TERMIOS tcgetattr(fd, &savetty);#else# if defined(_BSD43) || defined(_V7) ioctl(fd, TIOCGETP, &sg); ioctl(fd, TIOCGETC, &tch);# endif# ifdef _BSD43 ioctl(fd, TIOCLGET, &lsw);# endif#endif#ifdef TIOCMODG ioctl(fd, TIOCMODG, &m_word);#endif}/* * Restore the state of a port */void m_restorestate(fd)int fd;{#ifdef POSIX_TERMIOS tcsetattr(fd, TCSANOW, &savetty);#else# if defined(_BSD43) || defined(_V7) ioctl(fd, TIOCSETP, &sg); ioctl(fd, TIOCSETC, &tch);# endif# ifdef _BSD43 ioctl(fd, TIOCLSET, &lsw);# endif#endif#ifdef TIOCMODS ioctl(fd, TIOCMODS, &m_word);#endif}/* * Set the line status so that it will not kill our process * if the line hangs up. *//*ARGSUSED*/ void m_nohang(fd)int fd;{#ifdef POSIX_TERMIOS struct termios sgg; tcgetattr(fd, &sgg); sgg.c_cflag |= CLOCAL; tcsetattr(fd, TCSANOW, &sgg);#else# if defined (_BSD43) && defined(LNOHANG) int lsw; ioctl(fd, TIOCLGET, &lsw); lsw |= LNOHANG; ioctl(fd, TIOCLSET, &lsw);# endif# ifdef _COHERENT /* Doesn't know about this either, me thinks. */# endif#endif}/* * Set hangup on close on/off. */void m_hupcl(fd, on)int fd;int on;{ /* Eh, I don't know how to do this under BSD (yet..) */#ifdef POSIX_TERMIOS struct termios sgg; tcgetattr(fd, &sgg); if (on) sgg.c_cflag |= HUPCL; else sgg.c_cflag &= ~HUPCL; tcsetattr(fd, TCSANOW, &sgg);#endif}/* * Flush the buffers */void m_flush(fd)int fd;{/* Should I Posixify this, or not? */#ifdef TCFLSH ioctl(fd, TCFLSH, 2);#endif#ifdef TIOCFLUSH#ifdef _COHERENT ioctl(fd, TIOCFLUSH, 0);#else ioctl(fd, TIOCFLUSH, (void *)0);#endif#endif}/* * See if there is input waiting. * returns: 0=nothing, >0=something, -1=can't. */int m_readchk(fd)int fd;{#ifdef FIONREAD long i = -1; (void) ioctl(fd, FIONREAD, &i); return((int)i);#else# if defined(F_GETFL) && defined(O_NDELAY) int i, old; char c; old = fcntl(fd, F_GETFL, 0); (void) fcntl(fd, F_SETFL, old | O_NDELAY); i = read(fd, &c, 1); (void) fcntl(fd, F_SETFL, old); return(i);# else return(-1);# endif#endif}/* * Get maximum speed. * Returns maximum speed / 100. (192-1152) */int m_getmaxspd(){#ifdef B230400 return(2304);#elif defined(B115200) return(1152);#elif defined(B57600) return(576);#elif defined(B38400) return(384);#elif defined(EXTB) return(384);#elif defined(B19200) return(192);#elif defined(EXTA) return(192);#else return(96);#endif}/* * Set baudrate, parity and number of bits. */void m_setparms(fd, baudr, par, bits, stopb, hwf, swf)int fd;char *baudr;char *par;char *bits;char *stopb;int hwf;int swf;{ int spd = -1; int newbaud; int bit = bits[0];#ifdef POSIX_TERMIOS struct termios tty; tcgetattr(fd, &tty);#else /* POSIX_TERMIOS */ struct sgttyb tty; ioctl(fd, TIOCGETP, &tty);#endif /* POSIX_TERMIOS */ /* We generate mark and space parity ourself. */ if (bit == '7' && (par[0] == 'M' || par[0] == 'S')) bit = '8'; /* Check if 'baudr' is really a number */ if ((newbaud = (atol(baudr) / 100)) == 0 && baudr[0] != '0') newbaud = -1; switch(newbaud) { case 0:#ifdef B0 spd = B0; break;#else spd = 0; break;#endif case 3: spd = B300; break; case 6: spd = B600; break; case 12: spd = B1200; break; case 24: spd = B2400; break; case 48: spd = B4800; break; case 96: spd = B9600; break;#ifdef B19200 case 192: spd = B19200; break;#else /* B19200 */# ifdef EXTA case 192: spd = EXTA; break;# else /* EXTA */ case 192: spd = B9600; break;# endif /* EXTA */#endif /* B19200 */#ifdef B38400 case 384: spd = B38400; break;#else /* B38400 */# ifdef EXTB case 384: spd = EXTB; break;# else /* EXTB */ case 384: spd = B9600; break;# endif /* EXTB */#endif /* B38400 */#ifdef B57600 case 576: spd = B57600; break;#endif#ifdef B115200 case 1152: spd = B115200; break;#endif#ifdef B230400 case 2304: spd = B230400; break;#endif } #if defined (_BSD43) && !defined(POSIX_TERMIOS) if (spd != -1) tty.sg_ispeed = tty.sg_ospeed = spd; /* Number of bits is ignored */ tty.sg_flags = RAW | TANDEM; if (par[0] == 'E') tty.sg_flags |= EVENP; else if (par[0] == 'O') tty.sg_flags |= ODDP; else tty.sg_flags |= PASS8 | ANYP; ioctl(fd, TIOCSETP, &tty);# ifdef TIOCSDTR /* FIXME: huh? - MvS */ ioctl(fd, TIOCSDTR, 0);# endif#endif /* _BSD43 && !POSIX_TERMIOS */#if defined (_V7) && !defined(POSIX_TERMIOS) if (spd != -1) tty.sg_ispeed = tty.sg_ospeed = spd; tty.sg_flags = RAW; if (par[0] == 'E') tty.sg_flags |= EVENP; else if (par[0] == 'O') tty.sg_flags |= ODDP; ioctl(fd, TIOCSETP, &tty);#endif /* _V7 && !POSIX */#ifdef POSIX_TERMIOS if (spd != -1) { cfsetospeed(&tty, (speed_t)spd); cfsetispeed(&tty, (speed_t)spd); } switch (bit) { case '5': tty.c_cflag = (tty.c_cflag & ~CSIZE) | CS5; break; case '6': tty.c_cflag = (tty.c_cflag & ~CSIZE) | CS6; break; case '7': tty.c_cflag = (tty.c_cflag & ~CSIZE) | CS7; break; case '8': default: tty.c_cflag = (tty.c_cflag & ~CSIZE) | CS8; break; } /* Set into raw, no echo mode */ tty.c_iflag = IGNBRK; tty.c_lflag = 0; tty.c_oflag = 0; tty.c_cflag |= CLOCAL | CREAD;#ifdef _DCDFLOW tty.c_cflag &= ~CRTSCTS;#endif tty.c_cc[VMIN] = 1; tty.c_cc[VTIME] = 5; if (swf) tty.c_iflag |= IXON | IXOFF; else tty.c_iflag &= ~(IXON|IXOFF|IXANY); tty.c_cflag &= ~(PARENB | PARODD); if (par[0] == 'E') tty.c_cflag |= PARENB; else if (par[0] == 'O') tty.c_cflag |= (PARENB | PARODD); if (stopb[0] == '2') tty.c_cflag |= CSTOPB; else tty.c_cflag &= ~CSTOPB; tcsetattr(fd, TCSANOW, &tty); m_setrts(fd);#endif /* POSIX_TERMIOS */#ifndef _DCDFLOW m_sethwf(fd, hwf);#endif}/* * Wait for child and return pid + status */int m_wait(stt)int *stt;{#if defined (_BSD43) && !defined(POSIX_TERMIOS) int pid; union wait st1; pid = wait((void *)&st1); *stt = (unsigned)st1.w_retcode + 256 * (unsigned)st1.w_termsig; return(pid);#else int pid; int st1; pid = wait(&st1); *stt = (unsigned)WEXITSTATUS(st1) + 256 * (unsigned)WTERMSIG(st1); return(pid);#endif}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -