From 81c48925997bf6f3361b2ce7168e96e8145bad9b Mon Sep 17 00:00:00 2001 From: Gerhard Rieger Date: Fri, 23 Jan 2015 21:30:38 +0100 Subject: [PATCH] Function cfmakeraw() is simulated when missing --- CHANGES | 5 +++++ config.h.in | 3 +++ configure.in | 2 +- doc/socat.yo | 25 ++++++++++++++----------- xio-termios.h | 1 + xioopts.c | 15 +++++++++++++++ 6 files changed, 39 insertions(+), 12 deletions(-) diff --git a/CHANGES b/CHANGES index 2002f08..15b705d 100644 --- a/CHANGES +++ b/CHANGES @@ -89,6 +89,11 @@ corrections: Test: FDOUT_ERROR Issue reported by Hendrik. + Added option termios-cfmakeraw that calls cfmakeraw() and is preferred + over option raw which is now obsolote. On SysV systems this call is + simulated by appropriate setting. + Thanks to Youfu Zhang for reporting issue with option raw. + porting: Socat included instead of POSIX Thanks to John Spencer for reporting this issue. diff --git a/config.h.in b/config.h.in index 0b30c42..dabfbe2 100644 --- a/config.h.in +++ b/config.h.in @@ -459,6 +459,9 @@ /* Define if you have the /dev/ptc pseudo terminal multiplexer */ #undef HAVE_DEV_PTC +/* Define if you have the cfmakeraw() function */ +#undef HAVE_CFMAKERAW + /* Define if you have the long long type */ #undef HAVE_TYPE_LONGLONG diff --git a/configure.in b/configure.in index c8e953f..1ca574e 100644 --- a/configure.in +++ b/configure.in @@ -91,6 +91,7 @@ dnl Checks for setgrent, getgrent and endgrent. AC_CHECK_FUNCS(setgrent getgrent endgrent) dnl Checks for getgrouplist() /* BSD */ AC_CHECK_FUNCS(getgrouplist) +AC_CHECK_FUNCS(cfmakeraw) dnl Link libresolv if necessary (for Mac OS X) AC_SEARCH_LIBS([res_9_init], [resolv]) @@ -101,7 +102,6 @@ AC_CHECK_FUNC(hstrerror, , AC_CHECK_LIB(resolv, hstrerror, [LIBS="$LIBS -lresol AC_CHECK_FUNC(gethostent, , AC_CHECK_LIB(nsl, gethostent)) AC_CHECK_FUNC(setsockopt, , AC_CHECK_LIB(socket, setsockopt)) - dnl Check for function prototype and in lib dnl arg1: function name dnl arg2: required include files beyond sysincludes.h diff --git a/doc/socat.yo b/doc/socat.yo index b77cc57..afeaf3a 100644 --- a/doc/socat.yo +++ b/doc/socat.yo @@ -2426,12 +2426,16 @@ Note: On some operating systems, these options may not be available. Use link(ispeed)(OPTION_ISPEED) or link(ospeed)(OPTION_OSPEED) instead. label(OPTION_ECHO)dit(bf(tt(echo=))) - Enables or disables local echo (link(example)(EXAMPLE_OPTION_ECHO)). + Enables or disables local echo. label(OPTION_ICANON)dit(bf(tt(icanon=))) Sets or clears canonical mode, enabling line buffering and some special characters. label(OPTION_RAW)dit(bf(tt(raw))) - Sets raw mode, thus passing input and output almost unprocessed (link(example)(EXAMPLE_OPTION_RAW)). + Sets raw mode, thus passing input and output almost unprocessed. This option is obsolete, use option link(rawer)(OPTION_TERMIOS_RAWER) or link(cfmakeraw)(OPTION_TERMIOS_CFMAKERAW) instead. +label(OPTION_TERMIOS_RAWER)dit(bf(tt(rawer))) + Makes terminal rawer than link(raw)(OPTION_RAW) option. This option implicitly turns off echo. (link(example)(EXAMPLE_OPTION_TERMIOS_RAWER)). +label(OPTION_TERMIOS_CFMAKERAW)dit(bf(tt(cfmakeraw))) + Sets raw mode by invoking tt(cfmakeraw()) or by simulating this call. This option implicitly turns off echo. label(OPTION_IGNBRK)dit(bf(tt(ignbrk=))) Ignores or interpretes the BREAK character (e.g., ^C) label(OPTION_BRKINT)dit(bf(tt(brkint=))) @@ -3021,13 +3025,12 @@ at most 512 data bytes per packet (link(mss)(OPTION_MSS)). label(EXAMPLE_ADDRESS_GOPEN) -label(EXAMPLE_OPTION_RAW) -label(EXAMPLE_OPTION_ECHO) +label(EXAMPLE_OPTION_TERMIOS_RAWER) label(EXAMPLE_OPTION_ESCAPE) -dit(bf(tt(socat -,raw,echo=0,escape=0x0f /dev/ttyS0,raw,echo=0,crnl))) +dit(bf(tt(socat -,escape=0x0f /dev/ttyS0,rawer,crnl))) opens an interactive connection via the serial line, e.g. for talking with a -modem. link(raw)(OPTION_RAW) and link(echo)(OPTION_ECHO) set the console's and +modem. link(rawer)(OPTION_TERMIOS_RAWER) and link(echo)(OPTION_ECHO) set the console's and ttyS0's terminal parameters to practicable values, link(crnl)(OPTION_CRNL) converts to correct newline characters. link(escape)(OPTION_ESCAPE) allows to terminate the socat process with character control-O. @@ -3150,12 +3153,12 @@ label(EXAMPLE_OPTION_WAIT_SLAVE) label(EXAMPLE_OPTION_NONBLOCK) mancommand(\.LP) mancommand(\.nf) -mancommand(\fBsocat PTY,link=$HOME/dev/vmodem0,raw,echo=0,wait-slave \\\bf) -mancommand(\fBEXEC:"ssh modemserver.us.org socat - /dev/ttyS0,nonblock,raw,echo=0"\fP) +mancommand(\fBsocat PTY,link=$HOME/dev/vmodem0,rawer,wait-slave \\\bf) +mancommand(\fBEXEC:"ssh modemserver.us.org socat - /dev/ttyS0,nonblock,rawer"\fP) mancommand(\.fi) -htmlcommand(
socat PTY,link=$HOME/dev/vmodem0,raw,echo=0,wait-slave \
-EXEC:'"ssh modemserver.us.org socat - /dev/ttyS0,nonblock,raw,echo=0"'
) +htmlcommand(
socat PTY,link=$HOME/dev/vmodem0,rawer,wait-slave \
+EXEC:'"ssh modemserver.us.org socat - /dev/ttyS0,nonblock,rawer"'
) generates a pseudo terminal device (link(PTY)(ADDRESS_PTY)) on the client that can be reached under the @@ -3294,7 +3297,7 @@ may thus cause packet loss. label(EXAMPLE_INTERFACE) -dit(bf(tt(socat PTY,link=/var/run/ppp,raw,echo=0 INTERFACE:hdlc0))) +dit(bf(tt(socat PTY,link=/var/run/ppp,rawer INTERFACE:hdlc0))) circumvents the problem that pppd requires a serial device and thus might not be able to work on a synchronous line that is represented by a network device. diff --git a/xio-termios.h b/xio-termios.h index 7fd3550..e661446 100644 --- a/xio-termios.h +++ b/xio-termios.h @@ -139,6 +139,7 @@ extern const struct optdesc opt_ispeed; extern const struct optdesc opt_ospeed; extern const struct optdesc opt_termios_rawer; +extern const struct optdesc opt_termios_cfmakeraw; #if _WITH_TERMIOS /* otherwise tcflag_t might be reported undefined */ extern int xiotermios_setflag(int fd, int word, tcflag_t mask); diff --git a/xioopts.c b/xioopts.c index 94015f1..3b0f300 100644 --- a/xioopts.c +++ b/xioopts.c @@ -277,6 +277,7 @@ const struct optname optionnames[] = { IF_OPENSSL("capath", &opt_openssl_capath) IF_OPENSSL("cert", &opt_openssl_certificate) IF_OPENSSL("certificate", &opt_openssl_certificate) + IF_TERMIOS("cfmakeraw", &opt_termios_cfmakeraw) IF_ANY ("chroot", &opt_chroot) IF_ANY ("chroot-early", &opt_chroot_early) /*IF_TERMIOS("cibaud", &opt_cibaud)*/ @@ -3654,6 +3655,7 @@ int applyopts(int fd, struct opt *opts, enum e_phase phase) { termarg.c_iflag = 0; termarg.c_oflag = 0; termarg.c_lflag = 0; + termarg.c_cflag = (CS8); termarg.c_cc[VMIN] = 1; termarg.c_cc[VTIME] = 0; break; @@ -3744,6 +3746,19 @@ int applyopts(int fd, struct opt *opts, enum e_phase phase) { termarg.c_lflag |= (ISIG|ICANON|IEXTEN|ECHO|ECHOE|ECHOK|ECHOCTL|ECHOKE); /*! "sets characters to their default values... - which? */ break; + case OPT_TERMIOS_CFMAKERAW: +#if HAVE_CFMAKERAW + cfmakeraw(&termarg); +#else + /* these setting follow the Linux documenation of cfmakeraw */ + termarg.c_iflag &= + ~(IGNBRK|BRKINT|PARMRK|ISTRIP|INLCR|IGNCR|ICRNL|IXON); + termarg.c_oflag &= ~(OPOST); + termarg.c_lflag &= ~(ECHO|ECHONL|ICANON|ISIG|IEXTEN); + termarg.c_cflag &= ~(CSIZE|PARENB); + termarg.c_cflag |= (CS8); +#endif + break; default: Error("TERMIOS option not handled - internal error?"); }