--- xinu/sys/ttyread.c 2018/04/24 17:39:02 1.1.1.1 +++ xinu/sys/ttyread.c 2018/04/24 17:39:17 1.1.1.2 @@ -10,86 +10,61 @@ *------------------------------------------------------------------------ */ ttyread(devptr, buff, count) -struct devsw *devptr; -int count; -char *buff; + struct devsw *devptr; + int count; + char *buff; { - PStype ps; - register struct tty *iptr; - int avail, nread; - char ch, eofch; - int donow, dolater; + register struct tty *ttyp; + int avail, numread; +#ifdef DEBUG + dotrace("ttyread", &devptr, 3); +#endif if (count < 0) return(SYSERR); - disable(ps); - if ( (avail=scount((iptr= &tty[devptr->dvminor])->isem)) < 0) - avail = 0; - if (count == 0) { /* read whatever is available */ - if (avail == 0) { - restore(ps); - return(0); - } - count = avail; + disable(); + + avail = scount( (ttyp= &tty[devptr->dvminor])->isem ); + if ( (count = (count==0 ? avail : count)) == 0) { + restore(); + return(0); } - if (count < avail) { - donow = count; - dolater = 0; - } else { - donow = avail; - dolater = count - avail; + numread = count; + if (avail >= count) { + readcopy(buff, ttyp, count); + restore(); + return(numread); } - nread = 0; - if (donow > 0) { - ch = iptr->ibuff[iptr->itail++]; - if (iptr->itail >= IBUFLEN) - iptr->itail = 0; - if ( ((eofch=iptr->ieofc) == ch) && iptr->ieof) { - sreset(iptr->isem, avail-1); - restore(ps); - return(EOF); - } - *buff++ = ch; - for (nread=1 ; nread < donow ; ) { - ch = iptr->ibuff[iptr->itail]; - if ( (ch==eofch) && iptr->ieof) { - sreset(iptr->isem, avail - nread); - restore(ps); - return(nread); - } - *buff++ = ch; - if (++iptr->itail >= IBUFLEN) - iptr->itail = 0; - nread++; - if (ch == NEWLINE || ch == RETURN) { - sreset(iptr->isem, avail - nread); - restore(ps); - return(nread); - } - } - sreset(iptr->isem, avail - nread); + if (avail > 0) { + readcopy(buff, ttyp, avail); + buff += avail; + count -= avail; } - donow = nread; - for (nread=0 ; nread < dolater ; ) { - wait(iptr->isem); - ch = iptr->ibuff[iptr->itail]; - if (ch == iptr->ieofc && iptr->ieof) { - if (nread == 0 && donow == 0) { - if (++iptr->itail >= IBUFLEN) - iptr->itail = 0; - restore(ps); - return(EOF); - } - signal(iptr->isem); - break; - } - *buff++ = ch; - nread++; - if (++iptr->itail >= IBUFLEN) - iptr->itail = 0; - if (ch == NEWLINE || ch == RETURN) - break; + restore(); + for ( ; count>0 ; count--) + *buff++ = ttygetc(devptr); + return(numread); +} + +/*------------------------------------------------------------------------ + * readcopy - high speed copy procedure used by ttyread + *------------------------------------------------------------------------ + */ +LOCAL readcopy(buff,ttyp,count) +register char *buff; +struct tty *ttyp; +int count; +{ + register char *qtail, *qend, *uend; /* copy loop variables */ + + qtail = &ttyp->ibuff[ttyp->itail]; + qend = &ttyp->ibuff[IBUFLEN]; + uend = buff + count; + while ( buff < uend ) { + *buff++ = *qtail++; + if ( qtail >= qend ) + qtail = ttyp->ibuff; } - restore(ps); - return(donow + nread); + ttyp->itail = qtail-ttyp->ibuff; + sreset(ttyp->isem, scount(ttyp->isem)-count); }