1 /* $Id: pushback.c,v 1.2 2000/08/23 19:42:17 cory Exp $
4 Revision 1.2 2000/08/23 19:42:17 cory
5 Added support for more Unix platforms. The following code has been hacked
6 to work on AIX, Solaris, True 64, and HP-UX.
7 Added bigendian check. Probably works on most big and little endian platforms
10 Revision 1.1.1.1 1999/12/06 03:09:13 toast
15 Revision 1.1 1999/05/10 08:32:37 burnsbr
21 pushback.c - code for a pushback buffer to handle file I/O
22 Copyright (C) 1999 Bryan Burns
24 This program is free software; you can redistribute it and/or
25 modify it under the terms of the GNU General Public License
26 as published by the Free Software Foundation; either version 2
27 of the License, or (at your option) any later version.
29 This program is distributed in the hope that it will be useful,
30 but WITHOUT ANY WARRANTY; without even the implied warranty of
31 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
32 GNU General Public License for more details.
34 You should have received a copy of the GNU General Public License
35 along with this program; if not, write to the Free Software
36 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
46 static char rcsid[] = "$Id: pushback.c,v 1.2 2000/08/23 19:42:17 cory Exp $";
48 void pb_init(pb_file *pbf, int fd){
50 pbf->next = pbf->pb_buff;
54 int pb_push(pb_file *pbf, void *buff, int amt){
59 printf("%d bytes being pushed back to the buffer\n", amt);
62 /* determine how much we can take */
63 if((RDSZ - pbf->buff_amt) < amt)
64 in_amt = RDSZ - pbf->buff_amt;
71 /* figure out if we need to wrap around, and if so, by how much */
72 if(((pbf->pb_buff + RDSZ) - pbf->next) < in_amt)
73 wrap = in_amt - ((pbf->pb_buff + RDSZ) - pbf->next);
75 /* write everything up til the end of the buffer */
76 memcpy(pbf->next, buff, (in_amt - wrap));
78 /* finish writing what's wrapped around */
79 memcpy(pbf->pb_buff, ((char *)buff + (in_amt - wrap)), wrap);
81 /* update the buff_amt field */
82 pbf->buff_amt += in_amt;
85 printf("%d bytes we can't accept\n", (amt - in_amt));
92 int pb_read(pb_file *pbf, void *buff, int amt){
99 printf("%d bytes requested from us\n", amt);
101 while(out_amt < amt){
102 /* if our push-back buffer contains some data */
103 if(pbf->buff_amt > 0){
106 printf("giving data from buffer\n");
109 /* calculate how much we can actually give the caller */
110 if( (amt - out_amt) < pbf->buff_amt )
111 tmp = (amt - out_amt);
115 /* Determine if we're going to need to wrap around the buffer */
116 if(tmp > ((pbf->pb_buff + RDSZ) - pbf->next))
117 wrap = tmp - ((pbf->pb_buff + RDSZ) - pbf->next);
119 memcpy(bp, pbf->next, (tmp - wrap));
120 bp = &(((char *)bp)[tmp - wrap]);
122 /* If we need to wrap, read from the start of the buffer */
124 memcpy(bp, pbf->pb_buff, wrap);
125 bp = &(((char *)bp)[wrap]);
128 /* update the buff_amt field */
129 pbf->buff_amt -= tmp;
133 printf("%d bytes remaining in buffer\n", pbf->buff_amt);
136 /* if the buffer is empty, reset the next header to the front of the
137 buffer so subsequent pushbacks/reads won't have to wrap */
138 if(pbf->buff_amt == 0)
139 pbf->next = pbf->pb_buff;
145 printf("Reading from file..\n");
148 /* The pushback buffer was empty, so we just need to read from the file */
149 tmp = read(pbf->fd, bp, (amt - out_amt));
155 bp = &(((char *)bp)[tmp]);
160 printf("managed to read %d bytes\n", out_amt);