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