Index: ucom.c =================================================================== --- ucom.c (revision 190281) +++ ucom.c (working copy) @@ -186,7 +186,23 @@ ucom_attach_tty(struct ucom_softc *sc, int flags, int ucom_attach(struct ucom_softc *sc) { + int ivar; + /* + * For certain low speed / timing sensitive applications having the + * buffers too large causes data to be stuck in the queue too long. By + * adding a tuneable, users can lower the buffer size to what works for + * their application + */ + if (!resource_int_value(device_get_name(sc->sc_dev), + device_get_unit(sc->sc_dev), "buffersize", &ivar) && + (ivar > sc->sc_opkthdrlen && ivar <= sc->sc_ibufsize)) { + sc->sc_ibufsize = ivar; + sc->sc_obufsize = ivar - sc->sc_opkthdrlen; + sc->sc_ibufsizepad = ivar;; + device_printf(sc->sc_dev, "Setting buffers to %d\n", ivar); + } + ucom_attach_tty(sc, TS_CALLOUT, "U%d", device_get_unit(sc->sc_dev)); @@ -321,6 +337,7 @@ ucomopen(struct tty *tp, struct cdev *dev) sc->sc_state |= UCS_RXSTOP; ucomstartread(sc); + ucom_status_change(sc); sc->sc_poll = 1; Index: uftdi.c =================================================================== --- uftdi.c (revision 190281) +++ uftdi.c (working copy) @@ -55,6 +55,7 @@ __FBSDID("$FreeBSD$"); #include #include #include +#include #include #include @@ -121,6 +122,7 @@ static void uftdi_read(void *sc, int portno, u_cha static void uftdi_write(void *sc, int portno, u_char *to, u_char *from, u_int32_t *count); static void uftdi_break(void *sc, int portno, int onoff); + static int uftdi_getstatus(int); struct ucom_callback uftdi_callback = { uftdi_get_status, @@ -418,6 +420,7 @@ uftdi_open(void *vsc, int portno) usb_device_request_t req; usbd_status err; struct termios t; + uint8_t msr[2]; DPRINTF(("uftdi_open: sc=%p\n", sc)); @@ -449,6 +452,18 @@ uftdi_open(void *vsc, int portno) if (err) return (EIO); + /* Refresh MSR */ + req.bmRequestType = UT_READ_VENDOR_DEVICE; + req.bRequest = FTDI_SIO_GET_STATUS; + USETW(req.wValue, 0); + USETW(req.wIndex, portno); + USETW(req.wLength, sc->sc_type == UFTDI_TYPE_SIO ? 1 : 2); + err = usbd_do_request(ucom->sc_udev, &req, &msr); + if (err) + return (EIO); + sc->sc_msr = uftdi_getstatus(msr[0]); + sc->sc_lsr = 0; + return (0); } @@ -461,7 +476,7 @@ uftdi_read(void *vsc, int portno, u_char **ptr, u_ DPRINTFN(15,("uftdi_read: sc=%p, port=%d count=%d\n", sc, portno, *count)); - msr = FTDI_GET_MSR(*ptr); + msr = uftdi_getstatus(FTDI_GET_MSR(*ptr)); lsr = FTDI_GET_LSR(*ptr); #ifdef USB_DEBUG @@ -702,6 +717,23 @@ uftdi_break(void *vsc, int portno, int onoff) (void)usbd_do_request(ucom->sc_udev, &req, NULL); } +static int +uftdi_getstatus(int status) +{ + int msr; + + msr = 0; + if (status & FTDI_SIO_CTS_MASK) + msr |= SER_CTS; + if (status & FTDI_SIO_DSR_MASK) + msr |= SER_DSR; + if (status & FTDI_SIO_RI_MASK) + msr |= SER_RI; + if (status & FTDI_SIO_RLSD_MASK) + msr |= SER_DCD; + return (msr); +} + static device_method_t uftdi_methods[] = { /* Device interface */ DEVMETHOD(device_probe, uftdi_match),