[Midnightbsd-cvs] src [12297] trunk/sys/dev/usb/serial: add additional device.

laffer1 at midnightbsd.org laffer1 at midnightbsd.org
Sun Feb 2 16:21:14 EST 2020


Revision: 12297
          http://svnweb.midnightbsd.org/src/?rev=12297
Author:   laffer1
Date:     2020-02-02 16:21:13 -0500 (Sun, 02 Feb 2020)
Log Message:
-----------
add additional device.

Modified Paths:
--------------
    trunk/sys/dev/usb/serial/u3g.c
    trunk/sys/dev/usb/serial/uchcom.c
    trunk/sys/dev/usb/serial/uplcom.c

Modified: trunk/sys/dev/usb/serial/u3g.c
===================================================================
--- trunk/sys/dev/usb/serial/u3g.c	2020-02-02 21:19:40 UTC (rev 12296)
+++ trunk/sys/dev/usb/serial/u3g.c	2020-02-02 21:21:13 UTC (rev 12297)
@@ -17,7 +17,7 @@
  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
  *
- * $FreeBSD: stable/10/sys/dev/usb/serial/u3g.c 329304 2018-02-15 08:57:14Z hselasky $
+ * $FreeBSD: stable/10/sys/dev/usb/serial/u3g.c 342037 2018-12-13 10:34:26Z hselasky $
  */
 
 /*
@@ -214,6 +214,7 @@
 	U3G_DEV(ALINK, 3G, 0),
 	U3G_DEV(ALINK, 3GU, 0),
 	U3G_DEV(ALINK, DWM652U5, 0),
+	U3G_DEV(ALINK, SIM7600E, 0),
 	U3G_DEV(AMOI, H01, 0),
 	U3G_DEV(AMOI, H01A, 0),
 	U3G_DEV(AMOI, H02, 0),

Modified: trunk/sys/dev/usb/serial/uchcom.c
===================================================================
--- trunk/sys/dev/usb/serial/uchcom.c	2020-02-02 21:19:40 UTC (rev 12296)
+++ trunk/sys/dev/usb/serial/uchcom.c	2020-02-02 21:21:13 UTC (rev 12297)
@@ -57,7 +57,7 @@
  */
 
 #include <sys/cdefs.h>
-__FBSDID("$FreeBSD: stable/10/sys/dev/usb/serial/uchcom.c 263687 2014-03-24 13:48:04Z emaste $");
+__FBSDID("$FreeBSD: stable/10/sys/dev/usb/serial/uchcom.c 335627 2018-06-25 08:57:03Z avg $");
 
 /*
  * Driver for WinChipHead CH341/340, the worst USB-serial chip in the
@@ -121,11 +121,11 @@
 #define	UCHCOM_REG_BPS_MOD	0x14
 #define	UCHCOM_REG_BPS_PAD	0x0F
 #define	UCHCOM_REG_BREAK1	0x05
-#define	UCHCOM_REG_BREAK2	0x18
 #define	UCHCOM_REG_LCR1		0x18
 #define	UCHCOM_REG_LCR2		0x25
 
 #define	UCHCOM_VER_20		0x20
+#define	UCHCOM_VER_30		0x30
 
 #define	UCHCOM_BASE_UNKNOWN	0
 #define	UCHCOM_BPS_MOD_BASE	20000000
@@ -134,12 +134,14 @@
 #define	UCHCOM_DTR_MASK		0x20
 #define	UCHCOM_RTS_MASK		0x40
 
-#define	UCHCOM_BRK1_MASK	0x01
-#define	UCHCOM_BRK2_MASK	0x40
+#define	UCHCOM_BRK_MASK		0x01
 
 #define	UCHCOM_LCR1_MASK	0xAF
 #define	UCHCOM_LCR2_MASK	0x07
-#define	UCHCOM_LCR1_PARENB	0x80
+#define	UCHCOM_LCR1_RX		0x80
+#define	UCHCOM_LCR1_TX		0x40
+#define	UCHCOM_LCR1_PARENB	0x08
+#define	UCHCOM_LCR1_CS8		0x03
 #define	UCHCOM_LCR2_PAREVEN	0x07
 #define	UCHCOM_LCR2_PARODD	0x06
 #define	UCHCOM_LCR2_PARMARK	0x05
@@ -321,13 +323,17 @@
 
 	sc->sc_udev = uaa->device;
 
-	switch (uaa->info.bcdDevice) {
-	case UCHCOM_REV_CH340:
+	switch (uaa->info.idProduct) {
+	case USB_PRODUCT_WCH2_CH341SER:
 		device_printf(dev, "CH340 detected\n");
 		break;
-	default:
+	case USB_PRODUCT_WCH2_CH341SER_2:
 		device_printf(dev, "CH341 detected\n");
 		break;
+	default:
+		device_printf(dev, "New CH340/CH341 product 0x%04x detected\n",
+		    uaa->info.idProduct);
+		break;
 	}
 
 	iface_index = UCHCOM_IFACE_INDEX;
@@ -411,6 +417,8 @@
 	USETW(req.wIndex, index);
 	USETW(req.wLength, 0);
 
+	DPRINTF("WR REQ 0x%02X VAL 0x%04X IDX 0x%04X\n",
+	    reqno, value, index);
 	ucom_cfg_do_request(sc->sc_udev,
 	    &sc->sc_ucom, &req, NULL, 0, 1000);
 }
@@ -427,6 +435,8 @@
 	USETW(req.wIndex, index);
 	USETW(req.wLength, buflen);
 
+	DPRINTF("RD REQ 0x%02X VAL 0x%04X IDX 0x%04X LEN %d\n",
+	    reqno, value, index, buflen);
 	ucom_cfg_do_request(sc->sc_udev,
 	    &sc->sc_ucom, &req, buf, USB_SHORT_XFER_OK, 1000);
 }
@@ -501,6 +511,7 @@
 uchcom_update_version(struct uchcom_softc *sc)
 {
 	uchcom_get_version(sc, &sc->sc_version);
+	DPRINTF("Chip version: 0x%02x\n", sc->sc_version);
 }
 
 static void
@@ -546,17 +557,17 @@
 	uint8_t brk1;
 	uint8_t brk2;
 
-	uchcom_read_reg(sc, UCHCOM_REG_BREAK1, &brk1, UCHCOM_REG_BREAK2, &brk2);
+	uchcom_read_reg(sc, UCHCOM_REG_BREAK1, &brk1, UCHCOM_REG_LCR1, &brk2);
 	if (onoff) {
 		/* on - clear bits */
-		brk1 &= ~UCHCOM_BRK1_MASK;
-		brk2 &= ~UCHCOM_BRK2_MASK;
+		brk1 &= ~UCHCOM_BRK_MASK;
+		brk2 &= ~UCHCOM_LCR1_TX;
 	} else {
 		/* off - set bits */
-		brk1 |= UCHCOM_BRK1_MASK;
-		brk2 |= UCHCOM_BRK2_MASK;
+		brk1 |= UCHCOM_BRK_MASK;
+		brk2 |= UCHCOM_LCR1_TX;
 	}
-	uchcom_write_reg(sc, UCHCOM_REG_BREAK1, brk1, UCHCOM_REG_BREAK2, brk2);
+	uchcom_write_reg(sc, UCHCOM_REG_BREAK1, brk1, UCHCOM_REG_LCR1, brk2);
 }
 
 static int
@@ -608,8 +619,12 @@
 	if (uchcom_calc_divider_settings(&dv, rate))
 		return;
 
+	/*
+	 * According to linux code we need to set bit 7 of UCHCOM_REG_BPS_PRE,
+	 * otherwise the chip will buffer data.
+	 */
 	uchcom_write_reg(sc,
-	    UCHCOM_REG_BPS_PRE, dv.dv_prescaler,
+	    UCHCOM_REG_BPS_PRE, dv.dv_prescaler | 0x80,
 	    UCHCOM_REG_BPS_DIV, dv.dv_div);
 	uchcom_write_reg(sc,
 	    UCHCOM_REG_BPS_MOD, dv.dv_mod,
@@ -674,6 +689,10 @@
 	default:
 		return (EIO);
 	}
+	if ((t->c_cflag & CSTOPB) != 0)
+		return (EIO);
+	if ((t->c_cflag & PARENB) != 0)
+		return (EIO);
 
 	if (uchcom_calc_divider_settings(&dv, t->c_ospeed)) {
 		return (EIO);
@@ -686,11 +705,26 @@
 {
 	struct uchcom_softc *sc = ucom->sc_parent;
 
-	uchcom_get_version(sc, 0);
+	uchcom_get_version(sc, NULL);
 	uchcom_ctrl_write(sc, UCHCOM_REQ_RESET, 0, 0);
 	uchcom_set_baudrate(sc, t->c_ospeed);
-	uchcom_read_reg(sc, 0x18, 0, 0x25, 0);
-	uchcom_write_reg(sc, 0x18, 0x50, 0x25, 0x00);
+	if (sc->sc_version < UCHCOM_VER_30) {
+		uchcom_read_reg(sc, UCHCOM_REG_LCR1, NULL,
+		    UCHCOM_REG_LCR2, NULL);
+		uchcom_write_reg(sc, UCHCOM_REG_LCR1, 0x50,
+		    UCHCOM_REG_LCR2, 0x00);
+	} else {
+		/*
+		 * Set up line control:
+		 * - enable transmit and receive
+		 * - set 8n1 mode
+		 * To do: support other sizes, parity, stop bits.
+		 */
+		uchcom_write_reg(sc,
+		    UCHCOM_REG_LCR1,
+		    UCHCOM_LCR1_RX | UCHCOM_LCR1_TX | UCHCOM_LCR1_CS8,
+		    UCHCOM_REG_LCR2, 0x00);
+	}
 	uchcom_update_status(sc);
 	uchcom_ctrl_write(sc, UCHCOM_REQ_RESET, 0x501f, 0xd90a);
 	uchcom_set_baudrate(sc, t->c_ospeed);

Modified: trunk/sys/dev/usb/serial/uplcom.c
===================================================================
--- trunk/sys/dev/usb/serial/uplcom.c	2020-02-02 21:19:40 UTC (rev 12296)
+++ trunk/sys/dev/usb/serial/uplcom.c	2020-02-02 21:21:13 UTC (rev 12297)
@@ -2,7 +2,7 @@
 /*	$NetBSD: uplcom.c,v 1.21 2001/11/13 06:24:56 lukem Exp $	*/
 
 #include <sys/cdefs.h>
-__FBSDID("$FreeBSD: stable/10/sys/dev/usb/serial/uplcom.c 305557 2016-09-07 19:21:52Z dim $");
+__FBSDID("$FreeBSD: stable/10/sys/dev/usb/serial/uplcom.c 339853 2018-10-29 12:11:27Z hselasky $");
 
 /*-
  * Copyright (c) 2001-2003, 2005 Shunsuke Akiyama <akiyama at jp.FreeBSD.org>.
@@ -133,12 +133,20 @@
 #define	UPLCOM_SET_CRTSCTS		0x41
 #define	UPLCOM_SET_CRTSCTS_PL2303X	0x61
 #define	RSAQ_STATUS_CTS			0x80
+#define	RSAQ_STATUS_OVERRUN_ERROR	0x40
+#define	RSAQ_STATUS_PARITY_ERROR	0x20 
+#define	RSAQ_STATUS_FRAME_ERROR	0x10
+#define	RSAQ_STATUS_RING		0x08
+#define	RSAQ_STATUS_BREAK_ERROR	0x04
 #define	RSAQ_STATUS_DSR			0x02
 #define	RSAQ_STATUS_DCD			0x01
 
 #define	TYPE_PL2303			0
 #define	TYPE_PL2303HX			1
+#define	TYPE_PL2303HXD			2
 
+#define	UPLCOM_STATE_INDEX		8
+
 enum {
 	UPLCOM_BULK_DT_WR,
 	UPLCOM_BULK_DT_RD,
@@ -367,18 +375,49 @@
 
 	sc->sc_udev = uaa->device;
 
-	/* Determine the chip type.  This algorithm is taken from Linux. */
 	dd = usbd_get_device_descriptor(sc->sc_udev);
-	if (dd->bDeviceClass == 0x02)
-		sc->sc_chiptype = TYPE_PL2303;
-	else if (dd->bMaxPacketSize == 0x40)
+
+	switch (UGETW(dd->bcdDevice)) {
+	case 0x0300:
 		sc->sc_chiptype = TYPE_PL2303HX;
-	else
-		sc->sc_chiptype = TYPE_PL2303;
+		/* or TA, that is HX with external crystal */
+		break;
+	case 0x0400:
+		sc->sc_chiptype = TYPE_PL2303HXD;
+		/* or EA, that is HXD with ESD protection */
+		/* or RA, that has internal voltage level converter that works only up to 1Mbaud (!) */
+		break;
+	case 0x0500:
+		sc->sc_chiptype = TYPE_PL2303HXD;
+		/* in fact it's TB, that is HXD with external crystal */
+		break;
+	default:
+		/* NOTE: I have no info about the bcdDevice for the base PL2303 (up to 1.2Mbaud,
+		   only fixed rates) and for PL2303SA (8-pin chip, up to 115200 baud */
+		/* Determine the chip type.  This algorithm is taken from Linux. */
+		if (dd->bDeviceClass == 0x02)
+			sc->sc_chiptype = TYPE_PL2303;
+		else if (dd->bMaxPacketSize == 0x40)
+			sc->sc_chiptype = TYPE_PL2303HX;
+		else
+			sc->sc_chiptype = TYPE_PL2303;
+		break;
+	}
 
-	DPRINTF("chiptype: %s\n",
-	    (sc->sc_chiptype == TYPE_PL2303HX) ?
-	    "2303X" : "2303");
+	switch (sc->sc_chiptype) {
+	case TYPE_PL2303:
+		DPRINTF("chiptype: 2303\n");
+		break;
+	case TYPE_PL2303HX:
+		DPRINTF("chiptype: 2303HX/TA\n");
+		break;
+	case TYPE_PL2303HXD:
+		DPRINTF("chiptype: 2303HXD/TB/RA/EA\n");
+		break;
+	default:
+		DPRINTF("chiptype: unknown %d\n", sc->sc_chiptype);
+		break;
+	}
 
 	/*
 	 * USB-RSAQ1 has two interface
@@ -427,7 +466,7 @@
 		goto detach;
 	}
 
-	if (sc->sc_chiptype != TYPE_PL2303HX) {
+	if (sc->sc_chiptype == TYPE_PL2303) {
 		/* HX variants seem to lock up after a clear stall request. */
 		mtx_lock(&sc->sc_mtx);
 		usbd_xfer_set_stall(sc->sc_xfer[UPLCOM_BULK_DT_WR]);
@@ -434,6 +473,7 @@
 		usbd_xfer_set_stall(sc->sc_xfer[UPLCOM_BULK_DT_RD]);
 		mtx_unlock(&sc->sc_mtx);
 	} else {
+		/* reset upstream data pipes */
 		if (uplcom_pl2303_do(sc->sc_udev, UT_WRITE_VENDOR_DEVICE,
 		    UPLCOM_SET_REQUEST, 8, 0, 0) ||
 		    uplcom_pl2303_do(sc->sc_udev, UT_WRITE_VENDOR_DEVICE,
@@ -552,7 +592,7 @@
 	    || uplcom_pl2303_do(udev, UT_WRITE_VENDOR_DEVICE, UPLCOM_SET_REQUEST, 1, 0, 0))
 		return (EIO);
 
-	if (chiptype == TYPE_PL2303HX)
+	if (chiptype != TYPE_PL2303)
 		err = uplcom_pl2303_do(udev, UT_WRITE_VENDOR_DEVICE, UPLCOM_SET_REQUEST, 2, 0x44, 0);
 	else
 		err = uplcom_pl2303_do(udev, UT_WRITE_VENDOR_DEVICE, UPLCOM_SET_REQUEST, 2, 0x24, 0);
@@ -632,23 +672,52 @@
 	    &req, NULL, 0, 1000);
 }
 
+/*
+ * NOTE: These baud rates are officially supported, they can be written
+ * directly into dwDTERate register.
+ *
+ * Free baudrate setting is not supported by the base PL2303, and on
+ * other models it requires writing a divisor value to dwDTERate instead
+ * of the raw baudrate. The formula for divisor calculation is not published
+ * by the vendor, so it is speculative, though the official product homepage
+ * refers to the Linux module source as a reference implementation.
+ */
 static const uint32_t uplcom_rates[] = {
-	75, 150, 300, 600, 1200, 1800, 2400, 3600, 4800, 7200, 9600, 14400,
-	19200, 28800, 38400, 57600, 115200,
 	/*
-	 * Higher speeds are probably possible. PL2303X supports up to
-	 * 6Mb and can set any rate
+	 * Basic 'standard' speed rates, supported by all models
+	 * NOTE: 900 and 56000 actually works as well
 	 */
-	230400, 460800, 614400, 921600, 1228800
+	75, 150, 300, 600, 900, 1200, 1800, 2400, 3600, 4800, 7200, 9600, 14400,
+	19200, 28800, 38400, 56000, 57600, 115200,
+	/*
+	 * Advanced speed rates up to 6Mbs, supported by HX/TA and HXD/TB/EA/RA
+     * NOTE: regardless of the spec, 256000 does not work
+	 */
+	128000, 134400, 161280, 201600, 230400, 268800, 403200, 460800, 614400,
+	806400, 921600, 1228800, 2457600, 3000000, 6000000,
+	/*
+	 * Advanced speed rates up to 12, supported by HXD/TB/EA/RA
+	 */
+	12000000
 };
 
 #define	N_UPLCOM_RATES	(sizeof(uplcom_rates)/sizeof(uplcom_rates[0]))
 
 static int
+uplcom_baud_supported(unsigned int speed)
+{
+	int i;
+	for (i = 0; i < N_UPLCOM_RATES; i++) {
+		if (uplcom_rates[i] == speed)
+			return 1;
+	}
+	return 0;
+}
+
+static int
 uplcom_pre_param(struct ucom_softc *ucom, struct termios *t)
 {
 	struct uplcom_softc *sc = ucom->sc_parent;
-	uint8_t i;
 
 	DPRINTF("\n");
 
@@ -656,20 +725,27 @@
 	 * Check requested baud rate.
 	 *
 	 * The PL2303 can only set specific baud rates, up to 1228800 baud.
-	 * The PL2303X can set any baud rate up to 6Mb.
+	 * The PL2303HX can set any baud rate up to 6Mb.
 	 * The PL2303HX rev. D can set any baud rate up to 12Mb.
 	 *
-	 * XXX: We currently cannot identify the PL2303HX rev. D, so treat
-	 *      it the same as the PL2303X.
 	 */
-	if (sc->sc_chiptype != TYPE_PL2303HX) {
-		for (i = 0; i < N_UPLCOM_RATES; i++) {
-			if (uplcom_rates[i] == t->c_ospeed)
+
+	/* accept raw divisor data, if someone wants to do the math in user domain */
+	if (t->c_ospeed & 0x80000000)
+		return 0;
+	switch (sc->sc_chiptype) {
+		case TYPE_PL2303HXD:
+			if (t->c_ospeed <= 12000000)
 				return (0);
-		}
- 	} else {
-		if (t->c_ospeed <= 6000000)
-			return (0);
+			break;
+		case TYPE_PL2303HX:
+			if (t->c_ospeed <= 6000000)
+				return (0);
+			break;
+		default:
+			if (uplcom_baud_supported(t->c_ospeed))
+				return (0);
+			break;
 	}
 
 	DPRINTF("uplcom_param: bad baud rate (%d)\n", t->c_ospeed);
@@ -676,6 +752,48 @@
 	return (EIO);
 }
 
+static unsigned int
+uplcom_encode_baud_rate_divisor(uint8_t *buf, unsigned int baud)
+{
+	unsigned int baseline, mantissa, exponent;
+
+	/* Determine the baud rate divisor. This algorithm is taken from Linux. */
+	/*
+	 * Apparently the formula is:
+	 *   baudrate = baseline / (mantissa * 4^exponent)
+	 * where
+	 *   mantissa = buf[8:0]
+	 *   exponent = buf[11:9]
+	 */
+	if (baud == 0)
+		baud = 1;
+	baseline = 383385600;
+	mantissa = baseline / baud;
+	if (mantissa == 0)
+		mantissa = 1;
+	exponent = 0;
+	while (mantissa >= 512) {
+		if (exponent < 7) {
+			mantissa >>= 2;	/* divide by 4 */
+			exponent++;
+		} else {
+			/* Exponent is maxed. Trim mantissa and leave. This gives approx. 45.8 baud */
+			mantissa = 511;
+			break;
+		}
+	}
+
+	buf[3] = 0x80;
+	buf[2] = 0;
+	buf[1] = exponent << 1 | mantissa >> 8;
+	buf[0] = mantissa & 0xff;
+
+	/* Calculate and return the exact baud rate. */
+	baud = (baseline / mantissa) >> (exponent << 1);
+	DPRINTF("real baud rate will be %u\n", baud);
+
+	return baud;
+}
 static void
 uplcom_cfg_param(struct ucom_softc *ucom, struct termios *t)
 {
@@ -687,10 +805,24 @@
 
 	memset(&ls, 0, sizeof(ls));
 
-	USETDW(ls.dwDTERate, t->c_ospeed);
+	/*
+	 * NOTE: If unsupported baud rates are set directly, the PL2303* uses 9600 baud.
+	 */
+	if ((t->c_ospeed & 0x80000000) || uplcom_baud_supported(t->c_ospeed))
+		USETDW(ls.dwDTERate, t->c_ospeed);
+	else
+		t->c_ospeed = uplcom_encode_baud_rate_divisor((uint8_t*)&ls.dwDTERate, t->c_ospeed);
 
 	if (t->c_cflag & CSTOPB) {
-		ls.bCharFormat = UCDC_STOP_BIT_2;
+		if ((t->c_cflag & CSIZE) == CS5) {
+			/*
+			 * NOTE: Comply with "real" UARTs / RS232:
+			 *       use 1.5 instead of 2 stop bits with 5 data bits
+			 */
+			ls.bCharFormat = UCDC_STOP_BIT_1_5;
+		} else {
+			ls.bCharFormat = UCDC_STOP_BIT_2;
+		}
 	} else {
 		ls.bCharFormat = UCDC_STOP_BIT_1;
 	}
@@ -720,7 +852,7 @@
 		break;
 	}
 
-	DPRINTF("rate=%d fmt=%d parity=%d bits=%d\n",
+	DPRINTF("rate=0x%08x fmt=%d parity=%d bits=%d\n",
 	    UGETDW(ls.dwDTERate), ls.bCharFormat,
 	    ls.bParityType, ls.bDataBits);
 
@@ -741,7 +873,7 @@
 		req.bmRequestType = UT_WRITE_VENDOR_DEVICE;
 		req.bRequest = UPLCOM_SET_REQUEST;
 		USETW(req.wValue, 0);
-		if (sc->sc_chiptype == TYPE_PL2303HX)
+		if (sc->sc_chiptype != TYPE_PL2303)
 			USETW(req.wIndex, UPLCOM_SET_CRTSCTS_PL2303X);
 		else
 			USETW(req.wIndex, UPLCOM_SET_CRTSCTS);
@@ -831,18 +963,33 @@
 			pc = usbd_xfer_get_frame(xfer, 0);
 			usbd_copy_out(pc, 0, buf, sizeof(buf));
 
-			DPRINTF("status = 0x%02x\n", buf[8]);
+			DPRINTF("status = 0x%02x\n", buf[UPLCOM_STATE_INDEX]);
 
 			sc->sc_lsr = 0;
 			sc->sc_msr = 0;
 
-			if (buf[8] & RSAQ_STATUS_CTS) {
+			if (buf[UPLCOM_STATE_INDEX] & RSAQ_STATUS_CTS) {
 				sc->sc_msr |= SER_CTS;
 			}
-			if (buf[8] & RSAQ_STATUS_DSR) {
+			if (buf[UPLCOM_STATE_INDEX] & RSAQ_STATUS_OVERRUN_ERROR) {
+				sc->sc_lsr |= ULSR_OE;
+			}
+			if (buf[UPLCOM_STATE_INDEX] & RSAQ_STATUS_PARITY_ERROR) {
+				sc->sc_lsr |= ULSR_PE;
+			}
+			if (buf[UPLCOM_STATE_INDEX] & RSAQ_STATUS_FRAME_ERROR) {
+				sc->sc_lsr |= ULSR_FE;
+			}
+			if (buf[UPLCOM_STATE_INDEX] & RSAQ_STATUS_RING) {
+				sc->sc_msr |= SER_RI;
+			}
+			if (buf[UPLCOM_STATE_INDEX] & RSAQ_STATUS_BREAK_ERROR) {
+				sc->sc_lsr |= ULSR_BI;
+			}
+			if (buf[UPLCOM_STATE_INDEX] & RSAQ_STATUS_DSR) {
 				sc->sc_msr |= SER_DSR;
 			}
-			if (buf[8] & RSAQ_STATUS_DCD) {
+			if (buf[UPLCOM_STATE_INDEX] & RSAQ_STATUS_DCD) {
 				sc->sc_msr |= SER_DCD;
 			}
 			ucom_status_change(&sc->sc_ucom);



More information about the Midnightbsd-cvs mailing list