xref: /plan9/sys/src/libstdio/fread.c (revision 7dd7cddf99dd7472612f1413b4da293630e6b1bc)
13e12c5d1SDavid du Colombier /*
23e12c5d1SDavid du Colombier  * pANS stdio -- fread
33e12c5d1SDavid du Colombier  */
43e12c5d1SDavid du Colombier #include "iolib.h"
53e12c5d1SDavid du Colombier 
63e12c5d1SDavid du Colombier #define BIGN (BUFSIZ/2)
73e12c5d1SDavid du Colombier 
fread(void * p,long recl,long nrec,FILE * f)83e12c5d1SDavid du Colombier long fread(void *p, long recl, long nrec, FILE *f){
9*7dd7cddfSDavid du Colombier 	char *s;
103e12c5d1SDavid du Colombier 	int n, d, c;
113e12c5d1SDavid du Colombier 
123e12c5d1SDavid du Colombier 	s=(char *)p;
133e12c5d1SDavid du Colombier 	n=recl*nrec;
143e12c5d1SDavid du Colombier 	while(n>0){
153e12c5d1SDavid du Colombier 		d=f->wp-f->rp;
163e12c5d1SDavid du Colombier 		if(d>0){
173e12c5d1SDavid du Colombier 			if(d>n)
183e12c5d1SDavid du Colombier 				d=n;
193e12c5d1SDavid du Colombier 			memmove(s, f->rp, d);
203e12c5d1SDavid du Colombier 			f->rp+=d;
213e12c5d1SDavid du Colombier 		}else{
223e12c5d1SDavid du Colombier 			if(n >= BIGN && f->state==RD && !(f->flags&STRING) && f->buf!=f->unbuf){
233e12c5d1SDavid du Colombier 				d=read(f->fd, s, n);
243e12c5d1SDavid du Colombier 				if(d<=0){
253e12c5d1SDavid du Colombier 					f->state=(d==0)?END:ERR;
263e12c5d1SDavid du Colombier 					goto ret;
273e12c5d1SDavid du Colombier 				}
283e12c5d1SDavid du Colombier 			}else{
293e12c5d1SDavid du Colombier  				c=_IO_getc(f);
303e12c5d1SDavid du Colombier 				if(c==EOF)
313e12c5d1SDavid du Colombier 					goto ret;
323e12c5d1SDavid du Colombier 				*s=c;
333e12c5d1SDavid du Colombier 				d=1;
343e12c5d1SDavid du Colombier 			}
353e12c5d1SDavid du Colombier 		}
363e12c5d1SDavid du Colombier 		s+=d;
373e12c5d1SDavid du Colombier 		n-=d;
383e12c5d1SDavid du Colombier 	}
393e12c5d1SDavid du Colombier     ret:
403e12c5d1SDavid du Colombier 	return (s-(char *)p)/(recl?recl:1);
413e12c5d1SDavid du Colombier }
42