From bfeab10515b0d20ae6916521659339af305f9f36 Mon Sep 17 00:00:00 2001 From: Jef Driesen Date: Tue, 25 Mar 2014 19:44:05 +0100 Subject: [PATCH] Add support for modifying the receive latency. Currently this isn't used or needed anywhere, but the research has been done, and it would be silly to drop the knowledge. We may need it in the future. --- src/serial.h | 2 ++ src/serial_posix.c | 39 +++++++++++++++++++++++++++++++++++++++ src/serial_win32.c | 9 +++++++++ 3 files changed, 50 insertions(+) diff --git a/src/serial.h b/src/serial.h index 4b1e0f3..5a9d8ea 100644 --- a/src/serial.h +++ b/src/serial.h @@ -93,6 +93,8 @@ int serial_set_queue_size (serial_t *device, unsigned int input, unsigned int ou int serial_set_halfduplex (serial_t *device, int value); +int serial_set_latency (serial_t *device, unsigned int milliseconds); + int serial_read (serial_t *device, void* data, unsigned int size); int serial_write (serial_t *device, const void* data, unsigned int size); diff --git a/src/serial_posix.c b/src/serial_posix.c index 2748957..e365024 100644 --- a/src/serial_posix.c +++ b/src/serial_posix.c @@ -512,6 +512,45 @@ serial_set_halfduplex (serial_t *device, int value) return 0; } +int +serial_set_latency (serial_t *device, unsigned int milliseconds) +{ + if (device == NULL) + return -1; // EINVAL (Invalid argument) + +#if defined(TIOCGSERIAL) && defined(TIOCSSERIAL) + // Get the current settings. + struct serial_struct ss; + if (ioctl (device->fd, TIOCGSERIAL, &ss) != 0 && NOPTY) { + SYSERROR (device->context, errno); + return -1; + } + + // Set or clear the low latency flag. + if (milliseconds == 0) { + ss.flags |= ASYNC_LOW_LATENCY; + } else { + ss.flags &= ~ASYNC_LOW_LATENCY; + } + + // Apply the new settings. + if (ioctl (device->fd, TIOCSSERIAL, &ss) != 0 && NOPTY) { + SYSERROR (device->context, errno); + return -1; + } +#elif defined(IOSSDATALAT) + // Set the receive latency in microseconds. Serial drivers use this + // value to determine how often to dequeue characters received by + // the hardware. A value of zero restores the default value. + unsigned long usec = (milliseconds == 0 ? 1 : milliseconds * 1000); + if (ioctl (device->fd, IOSSDATALAT, &usec) != 0 && NOPTY) { + SYSERROR (device->context, errno); + return -1; + } +#endif + + return 0; +} int serial_read (serial_t *device, void *data, unsigned int size) diff --git a/src/serial_win32.c b/src/serial_win32.c index 2afb54d..9d5572c 100644 --- a/src/serial_win32.c +++ b/src/serial_win32.c @@ -389,6 +389,15 @@ serial_set_halfduplex (serial_t *device, int value) } +int +serial_set_latency (serial_t *device, unsigned int milliseconds) +{ + if (device == NULL) + return -1; // ERROR_INVALID_PARAMETER (The parameter is incorrect) + + return 0; +} + int serial_read (serial_t *device, void* data, unsigned int size) {