home *** CD-ROM | disk | FTP | other *** search
-
- /*
- * FREAD.C
- *
- * (c)Copyright 1990, Matthew Dillon, All Rights Reserved
- *
- * fread does not return EOF unless an error occurs. fread returns
- * 0 or < elms when the end of file is reached.
- */
-
- #include <stdio.h>
-
- #define buf ((char *)vbuf)
-
- size_t
- fread(vbuf, elmsize, elms, fi)
- void *vbuf;
- size_t elmsize;
- size_t elms;
- FILE *fi;
- {
- int bytes;
- int origBytes;
-
- if (elmsize == 1)
- bytes = elms;
- else if (elms == 1)
- bytes = elmsize;
- else
- bytes = elms * elmsize;
-
- origBytes = bytes;
-
- if (fi && (fi->sd_Flags & __SIF_READ) && !fi->sd_Error) {
- int n = 0; /* actual read */
-
- if (bytes == 0 || (fi->sd_Flags & __SIF_EOF))
- return(0);
-
- if (fi->sd_UC >= 0) { /* ungotten character */
- *buf++ = fi->sd_UC;
- fi->sd_UC = -1;
- --bytes;
- }
-
- if (fi->sd_RLeft > 0) {
- n = (fi->sd_RLeft > bytes) ? bytes : fi->sd_RLeft;
-
- movmem(fi->sd_RPtr, buf, n);
- fi->sd_RPtr += n;
- fi->sd_RLeft -= n;
- buf += n;
- bytes -= n;
- }
- if (bytes) {
- if (bytes < fi->sd_BufSiz) {
- if (_filbuf(fi)) /* on no more data return n */
- goto skip;
- }
- if (fi->sd_RLeft <= 0) { /* unbuffered read or too-large read */
- int nn;
-
- nn = read(fi->sd_Fd, buf, bytes);
- if (nn < 0) {
- if (n == 0)
- n = -1;
- } else {
- fi->sd_Offset += nn;
- n += nn;
- }
- } else {
- if (fi->sd_RLeft < bytes)
- bytes = fi->sd_RLeft;
- movmem(fi->sd_RPtr, buf, bytes);
- fi->sd_RPtr += bytes;
- fi->sd_RLeft -= bytes;
- n += bytes;
- }
- }
- skip:
- if (n < 0)
- fi->sd_Error = EOF;
- if (fi->sd_Error)
- return(fi->sd_Error);
- if (n == origBytes)
- return(elms);
- if (n == 0)
- return(0);
- return(n / elmsize);
- }
- return(EOF);
- }
-
-