From c0af4e4799ee02834cc8aaf7f1d81048c1292a45 Mon Sep 17 00:00:00 2001 From: Joel Sherrill Date: Thu, 16 Aug 2001 20:58:14 +0000 Subject: 2001-08-16 Mike Siers * libc/termios.c: Fix a bug in the termios implementation in the following scenario: The General Terminal Interface document that me states that if VMIN = 0 and VTIME = 0, then read() should return the minimum of two values: a) number of bytes available b) number of bytes requested (I assume from the read call) The current implementation of the fillBufferQueue() in termios.c is always return 1 character with these setting values. I know the termios buffer has more than one character available and my read() call is requesting 1024 bytes. --- cpukit/libcsupport/src/termios.c | 42 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) (limited to 'cpukit') diff --git a/cpukit/libcsupport/src/termios.c b/cpukit/libcsupport/src/termios.c index 0a23d5bc32..37a9e77213 100644 --- a/cpukit/libcsupport/src/termios.c +++ b/cpukit/libcsupport/src/termios.c @@ -190,6 +190,14 @@ rtems_termios_open ( rtems_semaphore_release (rtems_termios_ttyMutex); return RTEMS_NO_MEMORY; } + /* + * Initialize wakeup callbacks + */ + tty->tty_snd.sw_pfn = NULL; + tty->tty_snd.sw_arg = NULL; + tty->tty_rcv.sw_pfn = NULL; + tty->tty_rcv.sw_arg = NULL; + tty->tty_rcvwakeup = 0; /* * link tty */ @@ -497,6 +505,7 @@ rtems_termios_ioctl (void *arg) { rtems_libio_ioctl_args_t *args = arg; struct rtems_termios_tty *tty = args->iop->data1; + struct ttywakeup *wakeup = (struct ttywakeup *)args->buffer; rtems_status_code sc; args->ioctl_return = 0; @@ -561,6 +570,14 @@ rtems_termios_ioctl (void *arg) drainOutput (tty); break; + case RTEMS_IO_SNDWAKEUP: + tty->tty_snd = *wakeup; + break; + + case RTEMS_IO_RCVWAKEUP: + tty->tty_rcv = *wakeup; + break; + /* * FIXME: add various ioctl code handlers */ @@ -1059,6 +1076,7 @@ rtems_termios_read (void *arg) return sc; if (linesw[tty->t_line].l_read != NULL) { sc = linesw[tty->t_line].l_read(tty,args); + tty->tty_rcvwakeup = 0; rtems_semaphore_release (tty->isem); return sc; } @@ -1078,6 +1096,7 @@ rtems_termios_read (void *arg) count--; } args->bytes_moved = args->count - count; + tty->tty_rcvwakeup = 0; rtems_semaphore_release (tty->isem); return sc; } @@ -1116,6 +1135,14 @@ rtems_termios_enqueue_raw_characters (void *ttyp, char *buf, int len) c = *buf++; linesw[tty->t_line].l_rint(c,tty); } + + /* + * check to see if rcv wakeup callback was set + */ + if (( !tty->tty_rcvwakeup ) && ( tty->tty_rcv.sw_pfn != NULL )) { + (*tty->tty_rcv.sw_pfn)(&tty->termios, tty->tty_rcv.sw_arg); + tty->tty_rcvwakeup = 1; + } return 0; } @@ -1201,6 +1228,14 @@ rtems_termios_enqueue_raw_characters (void *ttyp, char *buf, int len) else { tty->rawInBuf.theBuf[newTail] = c; tty->rawInBuf.Tail = newTail; + + /* + * check to see if rcv wakeup callback was set + */ + if (( !tty->tty_rcvwakeup ) && ( tty->tty_rcv.sw_pfn != NULL )) { + (*tty->tty_rcv.sw_pfn)(&tty->termios, tty->tty_rcv.sw_arg); + tty->tty_rcvwakeup = 1; + } } } } @@ -1288,6 +1323,13 @@ rtems_termios_refill_transmitter (struct rtems_termios_tty *tty) */ tty->rawOutBufState = rob_idle; nToSend = 0; + + /* + * check to see if snd wakeup callback was set + */ + if ( tty->tty_snd.sw_pfn != NULL) { + (*tty->tty_snd.sw_pfn)(&tty->termios, tty->tty_snd.sw_arg); + } } /* check, whether output should stop due to received XOFF */ else if ((tty->flow_ctrl & (FL_MDXON | FL_ORCVXOF)) -- cgit v1.2.3