diff --git a/bin/stty/modes.c b/bin/stty/modes.c index e34afb83ee38..0fe4e5168d2c 100644 --- a/bin/stty/modes.c +++ b/bin/stty/modes.c @@ -91,6 +91,8 @@ static const struct modes cmodes[] = { { "-rtsflow", 0, CRTS_IFLOW }, { "mdmbuf", MDMBUF, 0 }, { "-mdmbuf", 0, MDMBUF }, + { "rtsdtr", 0, CNO_RTSDTR }, + { "-rtsdtr", CNO_RTSDTR, 0 }, { NULL, 0, 0 }, }; diff --git a/bin/stty/print.c b/bin/stty/print.c index 03d5c3b8a770..a76cd46b765e 100644 --- a/bin/stty/print.c +++ b/bin/stty/print.c @@ -184,6 +184,12 @@ print(struct termios *tp, struct winsize *wp, int ldisc, enum FMT fmt) put("-dsrflow", CDSR_OFLOW, 0); put("-dtrflow", CDTR_IFLOW, 0); put("-mdmbuf", MDMBUF, 0); /* XXX mdmbuf == dtrflow */ + if (on(CNO_RTSDTR)) + bput("-rtsdtr"); + else { + if (fmt >= BSD) + bput("rtsdtr"); + } /* special control characters */ cc = tp->c_cc; diff --git a/bin/stty/stty.1 b/bin/stty/stty.1 index a0f76fe2bfd1..1863c2286176 100644 --- a/bin/stty/stty.1 +++ b/bin/stty/stty.1 @@ -145,6 +145,8 @@ Assume a line without (with) modem control. .It Cm crtscts Pq Fl crtscts Enable (disable) RTS/CTS flow control. +.It Cm rtsdtr Pq Fl -rtsdtr +Enable (disable) asserting RTS/DTR on open. .El .Ss Input Modes: This corresponds to the c_iflag in the termios structure. diff --git a/share/man/man4/termios.4 b/share/man/man4/termios.4 index 6f38cf3b9f91..e3fb9635d247 100644 --- a/share/man/man4/termios.4 +++ b/share/man/man4/termios.4 @@ -1185,6 +1185,8 @@ flow control of output */ /* RTS flow control of input */ .It Dv MDMBUF /* flow control output via Carrier */ +.It Dv CNO_RTSDTR +/* Do not assert RTS or DTR automatically */ .El .Pp The @@ -1267,6 +1269,12 @@ If is set then output flow control is controlled by the state of Carrier Detect. .Pp +If +.Dv CNO_RTSDTR +is set then the RTS and DTR lines will not be asserted when the device +is opened. +As a result, this flag is only useful on initial-state devices. +.Pp If the object for which the control modes are set is not an asynchronous serial connection, some of the modes may be ignored; for example, if an attempt is made to set the baud rate on a network connection to a diff --git a/sys/dev/uart/uart_tty.c b/sys/dev/uart/uart_tty.c index 1bef6384678e..ad7052289f0b 100644 --- a/sys/dev/uart/uart_tty.c +++ b/sys/dev/uart/uart_tty.c @@ -285,13 +285,16 @@ uart_tty_param(struct tty *tp, struct termios *t) parity = UART_PARITY_NONE; if (UART_PARAM(sc, t->c_ospeed, databits, stopbits, parity) != 0) return (EINVAL); - UART_SETSIG(sc, SER_DDTR | SER_DTR); + if ((t->c_cflag & CNO_RTSDTR) == 0) + UART_SETSIG(sc, SER_DDTR | SER_DTR); /* Set input flow control state. */ if (!sc->sc_hwiflow) { if ((t->c_cflag & CRTS_IFLOW) && sc->sc_isquelch) UART_SETSIG(sc, SER_DRTS); - else - UART_SETSIG(sc, SER_DRTS | SER_RTS); + else { + if ((t->c_cflag & CNO_RTSDTR) == 0) + UART_SETSIG(sc, SER_DRTS | SER_RTS); + } } else UART_IOCTL(sc, UART_IOCTL_IFLOW, (t->c_cflag & CRTS_IFLOW)); /* Set output flow control state. */ diff --git a/sys/dev/usb/serial/umcs.c b/sys/dev/usb/serial/umcs.c index bcff8190344d..d314010b05b3 100644 --- a/sys/dev/usb/serial/umcs.c +++ b/sys/dev/usb/serial/umcs.c @@ -499,7 +499,9 @@ umcs7840_cfg_open(struct ucom_softc *ucom) * Enable DTR/RTS on modem control, enable modem interrupts -- * documented */ - sc->sc_ports[pn].sc_mcr = MCS7840_UART_MCR_DTR | MCS7840_UART_MCR_RTS | MCS7840_UART_MCR_IE; + sc->sc_ports[pn].sc_mcr = MCS7840_UART_MCR_IE; + if (ucom->sc_tty == NULL || (ucom->sc_tty->t_termios.c_cflag & CNO_RTSDTR) == 0) + sc->sc_ports[pn].sc_mcr |= MCS7840_UART_MCR_DTR | MCS7840_UART_MCR_RTS; if (umcs7840_set_UART_reg_sync(sc, pn, MCS7840_UART_REG_MCR, sc->sc_ports[pn].sc_mcr)) return; diff --git a/sys/dev/usb/serial/usb_serial.c b/sys/dev/usb/serial/usb_serial.c index 445c9f2127b8..698ad87c88fe 100644 --- a/sys/dev/usb/serial/usb_serial.c +++ b/sys/dev/usb/serial/usb_serial.c @@ -796,7 +796,8 @@ ucom_open(struct tty *tp) &sc->sc_start_task[0].hdr, &sc->sc_start_task[1].hdr); - ucom_modem(tp, SER_DTR | SER_RTS, 0); + if (sc->sc_tty == NULL || (sc->sc_tty->t_termios.c_cflag & CNO_RTSDTR) == 0) + ucom_modem(tp, SER_DTR | SER_RTS, 0); ucom_ring(sc, 0); diff --git a/sys/kern/tty.c b/sys/kern/tty.c index 022c392d5c17..90f6245eac8a 100644 --- a/sys/kern/tty.c +++ b/sys/kern/tty.c @@ -93,7 +93,7 @@ static const char *dev_console_filename; FLUSHO|NOKERNINFO|NOFLSH) #define TTYSUP_CFLAG (CIGNORE|CSIZE|CSTOPB|CREAD|PARENB|PARODD|\ HUPCL|CLOCAL|CCTS_OFLOW|CRTS_IFLOW|CDTR_IFLOW|\ - CDSR_OFLOW|CCAR_OFLOW) + CDSR_OFLOW|CCAR_OFLOW|CNO_RTSDTR) #define TTY_CALLOUT(tp,d) (dev2unit(d) & TTYUNIT_CALLOUT) @@ -332,7 +332,8 @@ ttydev_open(struct cdev *dev, int oflags, int devtype __unused, if (TTY_CALLOUT(tp, dev) || dev == dev_console) tp->t_termios.c_cflag |= CLOCAL; - ttydevsw_modem(tp, SER_DTR|SER_RTS, 0); + if ((tp->t_termios.c_cflag & CNO_RTSDTR) == 0) + ttydevsw_modem(tp, SER_DTR|SER_RTS, 0); error = ttydevsw_open(tp); if (error != 0) diff --git a/sys/sys/_termios.h b/sys/sys/_termios.h index 7a68dee99148..fab12cfa4064 100644 --- a/sys/sys/_termios.h +++ b/sys/sys/_termios.h @@ -143,6 +143,7 @@ #define CDTR_IFLOW 0x00040000 /* DTR flow control of input */ #define CDSR_OFLOW 0x00080000 /* DSR flow control of output */ #define CCAR_OFLOW 0x00100000 /* DCD flow control of output */ +#define CNO_RTSDTR 0x00200000 /* Do not assert RTS or DTR automatically */ #endif