From: Michael Westermann <mw@microdata-pos.de>
To: "Theodore Y. Ts'o" <tytso@MIT.EDU>
Cc: Rusty Russell <rusty@rustcorp.com.au>, linux-kernel@vger.kernel.org
Subject: [RFC] handshake variable with DTR DSR DCD ...
Date: Fri, 7 May 2004 16:54:13 +0200 [thread overview]
Message-ID: <20040507165413.D16132@microdata-pos.de> (raw)
Hello,
this is a patch to allow arbitrary serial status lines to be
used for hardware handshake. It's mainly useful for DTR/DSR
handshake.
diff -Nurp linux-2.4.26.old/drivers/char/serial.c linux-2.4.26/drivers/char/serial.c
--- linux-2.4.26.old/drivers/char/serial.c 2004-02-18 14:36:31.000000000 +0100
+++ linux-2.4.26/drivers/char/serial.c 2004-05-07 16:42:19.000000000 +0200
@@ -769,9 +769,12 @@ static _INLINE_ void check_modem_status(
}
if (info->flags & ASYNC_CTS_FLOW) {
if (info->tty->hw_stopped) {
- if (status & UART_MSR_CTS) {
+ if (status & info->status_flow) {
#if (defined(SERIAL_DEBUG_INTR) || defined(SERIAL_DEBUG_FLOW))
- printk("CTS tx start...");
+ if (info->status_flow & UART_MSR_CTS)
+ printk("CTS tx start...");
+ else
+ printk("HW %x tx start...", info->status_flow);
#endif
info->tty->hw_stopped = 0;
info->IER |= UART_IER_THRI;
@@ -780,9 +783,12 @@ static _INLINE_ void check_modem_status(
return;
}
} else {
- if (!(status & UART_MSR_CTS)) {
+ if (!(status & info->status_flow)) {
#if (defined(SERIAL_DEBUG_INTR) || defined(SERIAL_DEBUG_FLOW))
- printk("CTS tx stop...");
+ if (info->status_flow & UART_MSR_CTS)
+ printk("CTS tx stop...");
+ else
+ printk("HW %x tx stop...", info->status_flow);
#endif
info->tty->hw_stopped = 1;
info->IER &= ~UART_IER_THRI;
@@ -1749,9 +1755,13 @@ static void change_speed(struct async_st
info->IER &= ~UART_IER_MSI;
if (info->flags & ASYNC_HARDPPS_CD)
info->IER |= UART_IER_MSI;
- if (cflag & CRTSCTS) {
+ if (cflag & (CRTSCTS|CHWFLOW)) {
info->flags |= ASYNC_CTS_FLOW;
info->IER |= UART_IER_MSI;
+ if (!(cflag & CHWFLOW)) {
+ info->status_flow = UART_MSR_CTS;
+ info->modem_flow = UART_MCR_RTS;
+ }
} else
info->flags &= ~ASYNC_CTS_FLOW;
if (cflag & CLOCAL)
@@ -2018,8 +2028,8 @@ static void rs_throttle(struct tty_struc
if (I_IXOFF(tty))
rs_send_xchar(tty, STOP_CHAR(tty));
- if (tty->termios->c_cflag & CRTSCTS)
- info->MCR &= ~UART_MCR_RTS;
+ if (tty->termios->c_cflag & (CRTSCTS|CHWFLOW))
+ info->MCR &= ~info->modem_flow;
save_flags(flags); cli();
serial_out(info, UART_MCR, info->MCR);
@@ -2046,8 +2056,8 @@ static void rs_unthrottle(struct tty_str
else
rs_send_xchar(tty, START_CHAR(tty));
}
- if (tty->termios->c_cflag & CRTSCTS)
- info->MCR |= UART_MCR_RTS;
+ if (tty->termios->c_cflag & (CRTSCTS|CHWFLOW))
+ info->MCR |= info->modem_flow;
save_flags(flags); cli();
serial_out(info, UART_MCR, info->MCR);
restore_flags(flags);
@@ -2352,6 +2362,46 @@ static int set_modem_info(struct async_s
| ((arg & TIOCM_LOOP) ? UART_MCR_LOOP : 0)
| ((arg & TIOCM_DTR) ? UART_MCR_DTR : 0));
break;
+ case TIOHWFLOWBIS:
+ if (arg & TIOCM_RTS)
+ info->modem_flow |= UART_MCR_RTS;
+ if (arg & TIOCM_DTR)
+ info->modem_flow |= UART_MCR_DTR;
+#ifdef TIOCM_OUT1
+ if (arg & TIOCM_OUT1)
+ info->modem_flow |= UART_MCR_OUT1;
+ if (arg & TIOCM_OUT2)
+ info->modem_flow |= UART_MCR_OUT2;
+#endif
+ if (arg & TIOCM_CTS)
+ info->status_flow |= UART_MSR_CTS;
+ if (arg & TIOCM_DSR)
+ info->status_flow |= UART_MSR_DSR;
+ if (arg & TIOCM_RI)
+ info->status_flow |= UART_MSR_RI;
+ if (arg & TIOCM_CD)
+ info->status_flow |= UART_MSR_DCD;
+ break;
+ case TIOHWFLOWBIC:
+ if (arg & TIOCM_RTS)
+ info->modem_flow &= ~UART_MCR_RTS;
+ if (arg & TIOCM_DTR)
+ info->modem_flow &= ~UART_MCR_DTR;
+#ifdef TIOCM_OUT1
+ if (arg & TIOCM_OUT1)
+ info->modem_flow &= ~UART_MCR_OUT1;
+ if (arg & TIOCM_OUT2)
+ info->modem_flow &= ~UART_MCR_OUT2;
+#endif
+ if (arg & TIOCM_CTS)
+ info->status_flow &= ~UART_MSR_CTS;
+ if (arg & TIOCM_DSR)
+ info->status_flow &= ~UART_MSR_DSR;
+ if (arg & TIOCM_RI)
+ info->status_flow &= ~UART_MSR_RI;
+ if (arg & TIOCM_CD)
+ info->status_flow &= ~UART_MSR_DCD;
+ break;
default:
return -EINVAL;
}
@@ -2605,6 +2655,8 @@ static int rs_ioctl(struct tty_struct *t
#endif
case TIOCMGET:
return get_modem_info(info, (unsigned int *) arg);
+ case TIOHWFLOWBIS:
+ case TIOHWFLOWBIC:
case TIOCMBIS:
case TIOCMBIC:
case TIOCMSET:
@@ -2734,9 +2786,9 @@ static void rs_set_termios(struct tty_st
if (!(old_termios->c_cflag & CBAUD) &&
(cflag & CBAUD)) {
info->MCR |= UART_MCR_DTR;
- if (!(tty->termios->c_cflag & CRTSCTS) ||
+ if (!(tty->termios->c_cflag & (CRTSCTS|CHWFLOW)) ||
!test_bit(TTY_THROTTLED, &tty->flags)) {
- info->MCR |= UART_MCR_RTS;
+ info->MCR |= info->status_flow;
}
save_flags(flags); cli();
serial_out(info, UART_MCR, info->MCR);
@@ -2744,8 +2796,8 @@ static void rs_set_termios(struct tty_st
}
/* Handle turning off CRTSCTS */
- if ((old_termios->c_cflag & CRTSCTS) &&
- !(tty->termios->c_cflag & CRTSCTS)) {
+ if ((old_termios->c_cflag & (CRTSCTS|CHWFLOW)) &&
+ !(tty->termios->c_cflag & (CRTSCTS|CHWFLOW))) {
tty->hw_stopped = 0;
rs_start(tty);
}
diff -Nurp linux-2.4.26.old/include/asm-i386/ioctls.h linux-2.4.26/include/asm-i386/ioctls.h
--- linux-2.4.26.old/include/asm-i386/ioctls.h 2003-08-25 13:44:43.000000000 +0200
+++ linux-2.4.26/include/asm-i386/ioctls.h 2004-05-07 13:48:28.000000000 +0200
@@ -68,6 +68,8 @@
#define TIOCGHAYESESP 0x545E /* Get Hayes ESP configuration */
#define TIOCSHAYESESP 0x545F /* Set Hayes ESP configuration */
#define FIOQSIZE 0x5460
+#define TIOHWFLOWBIS 0x5461 /* Set hardware flow Control */
+#define TIOHWFLOWBIC 0x5462 /* Clear hardware flow Control */
/* Used for packet mode */
#define TIOCPKT_DATA 0
diff -Nurp linux-2.4.26.old/include/asm-i386/termbits.h linux-2.4.26/include/asm-i386/termbits.h
--- linux-2.4.26.old/include/asm-i386/termbits.h 2000-01-21 01:05:26.000000000 +0100
+++ linux-2.4.26/include/asm-i386/termbits.h 2004-05-07 16:43:39.000000000 +0200
@@ -132,6 +132,7 @@ struct termios {
#define B3000000 0010015
#define B3500000 0010016
#define B4000000 0010017
+#define CHWFLOW 001000000000 /* flexible hw flow_ctrl */
#define CIBAUD 002003600000 /* input baud rate (not used) */
#define CMSPAR 010000000000 /* mark or space (stick) parity */
#define CRTSCTS 020000000000 /* flow control */
diff -Nurp linux-2.4.26.old/include/linux/serialP.h linux-2.4.26/include/linux/serialP.h
--- linux-2.4.26.old/include/linux/serialP.h 2002-08-03 02:39:45.000000000 +0200
+++ linux-2.4.26/include/linux/serialP.h 2004-05-07 14:06:30.000000000 +0200
@@ -68,6 +68,8 @@ struct async_struct {
int timeout;
int quot;
int x_char; /* xon/xoff character */
+ int status_flow; /* status mask hw-flowcontrol */
+ int modem_flow; /* modem mask hw-flowcontrol */
int close_delay;
unsigned short closing_wait;
unsigned short closing_wait2;
It's only i386 yet, but please comment on it!
next reply other threads:[~2004-05-07 14:54 UTC|newest]
Thread overview: 2+ messages / expand[flat|nested] mbox.gz Atom feed top
2004-05-07 14:54 Michael Westermann [this message]
2004-05-07 18:11 ` [RFC] handshake variable with DTR DSR DCD Jan-Benedict Glaw
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20040507165413.D16132@microdata-pos.de \
--to=mw@microdata-pos.de \
--cc=linux-kernel@vger.kernel.org \
--cc=rusty@rustcorp.com.au \
--cc=tytso@MIT.EDU \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.