unix/fiss

lib/libbio/brdline.c in master
Repositories | Summary | Log | Files | LICENSE

brdline.c (1567B) download


 1#include "lib9.h"
 2
 3#include <bio.h>
 4
 5void* Brdline(Biobuf* bp, int delim) {
 6	char *ip, *ep;
 7	int   i, j;
 8
 9	i = -bp->icount;
10	if (i == 0) {
11		/*
12		 * eof or other error
13		 */
14		if (bp->state != Bractive) {
15			if (bp->state == Bracteof)
16				bp->state = Bractive;
17			bp->rdline = 0;
18			bp->gbuf   = bp->ebuf;
19			return 0;
20		}
21	}
22
23	/*
24	 * first try in remainder of buffer (gbuf doesn't change)
25	 */
26	ip = (char*) bp->ebuf - i;
27	ep = memchr(ip, delim, i);
28	if (ep) {
29		j          = (ep - ip) + 1;
30		bp->rdline = j;
31		bp->icount += j;
32		return ip;
33	}
34
35	/*
36	 * copy data to beginning of buffer
37	 */
38	if (i < bp->bsize)
39		memmove(bp->bbuf, ip, i);
40	bp->gbuf = bp->bbuf;
41
42	/*
43	 * append to buffer looking for the delim
44	 */
45	ip = (char*) bp->bbuf + i;
46	while (i < bp->bsize) {
47		j = read(bp->fid, ip, bp->bsize - i);
48		if (j <= 0) {
49			/*
50			 * end of file with no delim
51			 */
52			memmove(bp->ebuf - i, bp->bbuf, i);
53			bp->rdline = i;
54			bp->icount = -i;
55			bp->gbuf   = bp->ebuf - i;
56			return 0;
57		}
58		bp->offset += j;
59		i += j;
60		ep = memchr(ip, delim, j);
61		if (ep) {
62			/*
63			 * found in new piece
64			 * copy back up and reset everything
65			 */
66			ip = (char*) bp->ebuf - i;
67			if (i < bp->bsize) {
68				memmove(ip, bp->bbuf, i);
69				bp->gbuf = (unsigned char*) ip;
70			}
71			j          = (ep - (char*) bp->bbuf) + 1;
72			bp->rdline = j;
73			bp->icount = j - i;
74			return ip;
75		}
76		ip += j;
77	}
78
79	/*
80	 * full buffer without finding
81	 */
82	bp->rdline = bp->bsize;
83	bp->icount = -bp->bsize;
84	bp->gbuf   = bp->bbuf;
85	return 0;
86}
87
88int Blinelen(Biobuf* bp) {
89
90	return bp->rdline;
91}