]> sourceware.org Git - glibc.git/blame - libio/genops.c
Update.
[glibc.git] / libio / genops.c
CommitLineData
40a55d20
UD
1/* Copyright (C) 1993, 1995, 1997 Free Software Foundation, Inc.
2 This file is part of the GNU IO Library.
3
4 This library is free software; you can redistribute it and/or
5 modify it under the terms of the GNU General Public License as
6 published by the Free Software Foundation; either version 2, or (at
7 your option) any later version.
8
9 This library is distributed in the hope that it will be useful, but
10 WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 General Public License for more details.
13
14 You should have received a copy of the GNU General Public License
15 along with this library; see the file COPYING. If not, write to
16 the Free Software Foundation, 59 Temple Place - Suite 330, Boston,
17 MA 02111-1307, USA.
18
19 As a special exception, if you link this library with files
20 compiled with a GNU compiler to produce an executable, this does
21 not cause the resulting executable to be covered by the GNU General
22 Public License. This exception does not however invalidate any
23 other reasons why the executable file might be covered by the GNU
24 General Public License. */
96aa2d94
RM
25
26/* Generic or default I/O operations. */
27
28#include "libioP.h"
29#ifdef __STDC__
30#include <stdlib.h>
31#endif
32#include <string.h>
33
34void
40a55d20
UD
35_IO_un_link (fp)
36 _IO_FILE *fp;
37{
38 if (fp->_flags & _IO_LINKED)
39 {
40 _IO_FILE **f;
41 for (f = &_IO_list_all; *f != NULL; f = &(*f)->_chain)
42 {
43 if (*f == fp)
44 {
45 *f = fp->_chain;
46 break;
47 }
48 }
49 fp->_flags &= ~_IO_LINKED;
96aa2d94 50 }
96aa2d94
RM
51}
52
53void
40a55d20
UD
54_IO_link_in (fp)
55 _IO_FILE *fp;
96aa2d94 56{
40a55d20
UD
57 if ((fp->_flags & _IO_LINKED) == 0)
58 {
96aa2d94
RM
59 fp->_flags |= _IO_LINKED;
60 fp->_chain = _IO_list_all;
61 _IO_list_all = fp;
40a55d20 62 }
96aa2d94
RM
63}
64
65/* Return minimum _pos markers
66 Assumes the current get area is the main get area. */
40a55d20 67static _IO_size_t _IO_least_marker __P ((_IO_FILE *fp));
96aa2d94 68
40a55d20
UD
69static _IO_size_t
70_IO_least_marker (fp)
71 _IO_FILE *fp;
96aa2d94
RM
72{
73 _IO_ssize_t least_so_far = fp->_IO_read_end - fp->_IO_read_base;
40a55d20 74 struct _IO_marker *mark;
96aa2d94
RM
75 for (mark = fp->_markers; mark != NULL; mark = mark->_next)
76 if (mark->_pos < least_so_far)
77 least_so_far = mark->_pos;
78 return least_so_far;
79}
80
81/* Switch current get area from backup buffer to (start of) main get area. */
82
83void
40a55d20
UD
84_IO_switch_to_main_get_area (fp)
85 _IO_FILE *fp;
96aa2d94
RM
86{
87 char *tmp;
88 fp->_flags &= ~_IO_IN_BACKUP;
89 /* Swap _IO_read_end and _IO_save_end. */
40a55d20
UD
90 tmp = fp->_IO_read_end;
91 fp->_IO_read_end = fp->_IO_save_end;
92 fp->_IO_save_end= tmp;
96aa2d94 93 /* Swap _IO_read_base and _IO_save_base. */
40a55d20
UD
94 tmp = fp->_IO_read_base;
95 fp->_IO_read_base = fp->_IO_save_base;
96 fp->_IO_save_base = tmp;
97
96aa2d94
RM
98 fp->_IO_read_ptr = fp->_IO_read_base;
99}
100
101/* Switch current get area from main get area to (end of) backup area. */
102
103void
40a55d20
UD
104_IO_switch_to_backup_area (fp)
105 _IO_FILE *fp;
96aa2d94
RM
106{
107 char *tmp;
108 fp->_flags |= _IO_IN_BACKUP;
109 /* Swap _IO_read_end and _IO_save_end. */
40a55d20
UD
110 tmp = fp->_IO_read_end;
111 fp->_IO_read_end = fp->_IO_save_end;
112 fp->_IO_save_end = tmp;
96aa2d94 113 /* Swap _gbase and _IO_save_base. */
40a55d20
UD
114 tmp = fp->_IO_read_base;
115 fp->_IO_read_base = fp->_IO_save_base;
116 fp->_IO_save_base = tmp;
117
96aa2d94
RM
118 fp->_IO_read_ptr = fp->_IO_read_end;
119}
120
121int
40a55d20
UD
122_IO_switch_to_get_mode (fp)
123 _IO_FILE *fp;
96aa2d94
RM
124{
125 if (fp->_IO_write_ptr > fp->_IO_write_base)
126 if (_IO_OVERFLOW (fp, EOF) == EOF)
127 return EOF;
40a55d20 128 if (_IO_in_backup (fp))
96aa2d94
RM
129 fp->_IO_read_base = fp->_IO_backup_base;
130 else
131 {
132 fp->_IO_read_base = fp->_IO_buf_base;
133 if (fp->_IO_write_ptr > fp->_IO_read_end)
134 fp->_IO_read_end = fp->_IO_write_ptr;
135 }
136 fp->_IO_read_ptr = fp->_IO_write_ptr;
137
138 fp->_IO_write_base = fp->_IO_write_ptr = fp->_IO_write_end = fp->_IO_read_ptr;
139
140 fp->_flags &= ~_IO_CURRENTLY_PUTTING;
141 return 0;
142}
143
144void
40a55d20
UD
145_IO_free_backup_area (fp)
146 _IO_FILE *fp;
96aa2d94
RM
147{
148 if (_IO_in_backup (fp))
40a55d20 149 _IO_switch_to_main_get_area (fp); /* Just in case. */
96aa2d94
RM
150 free (fp->_IO_save_base);
151 fp->_IO_save_base = NULL;
152 fp->_IO_save_end = NULL;
153 fp->_IO_backup_base = NULL;
154}
155
156#if 0
157int
40a55d20
UD
158_IO_switch_to_put_mode (fp)
159 _IO_FILE *fp;
96aa2d94
RM
160{
161 fp->_IO_write_base = fp->_IO_read_ptr;
162 fp->_IO_write_ptr = fp->_IO_read_ptr;
163 /* Following is wrong if line- or un-buffered? */
40a55d20
UD
164 fp->_IO_write_end = (fp->_flags & _IO_IN_BACKUP
165 ? fp->_IO_read_end : fp->_IO_buf_end);
96aa2d94
RM
166
167 fp->_IO_read_ptr = fp->_IO_read_end;
168 fp->_IO_read_base = fp->_IO_read_end;
169
170 fp->_flags |= _IO_CURRENTLY_PUTTING;
171 return 0;
172}
173#endif
174
175int
40a55d20
UD
176__overflow (f, ch)
177 _IO_FILE *f;
178 int ch;
96aa2d94
RM
179{
180 return _IO_OVERFLOW (f, ch);
181}
182
dfd2257a
UD
183static int save_for_backup __P ((_IO_FILE *fp))
184#ifdef _LIBC
185 internal_function
186#endif
187 ;
40a55d20
UD
188
189 static int
dfd2257a
UD
190#ifdef _LIBC
191 internal_function
192#endif
40a55d20
UD
193save_for_backup (fp)
194 _IO_FILE *fp;
96aa2d94
RM
195{
196 /* Append [_IO_read_base.._IO_read_end] to backup area. */
40a55d20 197 int least_mark = _IO_least_marker (fp);
96aa2d94
RM
198 /* needed_size is how much space we need in the backup area. */
199 int needed_size = (fp->_IO_read_end - fp->_IO_read_base) - least_mark;
200 int current_Bsize = fp->_IO_save_end - fp->_IO_save_base;
201 int avail; /* Extra space available for future expansion. */
202 int delta;
203 struct _IO_marker *mark;
204 if (needed_size > current_Bsize)
205 {
206 char *new_buffer;
207 avail = 100;
40a55d20 208 new_buffer = (char *) malloc (avail + needed_size);
96aa2d94
RM
209 if (new_buffer == NULL)
210 return EOF; /* FIXME */
211 if (least_mark < 0)
212 {
40a55d20
UD
213 memcpy (new_buffer + avail,
214 fp->_IO_save_end + least_mark,
215 -least_mark);
216 memcpy (new_buffer + avail - least_mark,
217 fp->_IO_read_base,
218 fp->_IO_read_end - fp->_IO_read_base);
96aa2d94
RM
219 }
220 else
40a55d20
UD
221 memcpy (new_buffer + avail,
222 fp->_IO_read_base + least_mark,
223 needed_size);
96aa2d94
RM
224 if (fp->_IO_save_base)
225 free (fp->_IO_save_base);
226 fp->_IO_save_base = new_buffer;
227 fp->_IO_save_end = new_buffer + avail + needed_size;
228 }
229 else
230 {
231 avail = current_Bsize - needed_size;
232 if (least_mark < 0)
233 {
40a55d20
UD
234 memmove (fp->_IO_save_base + avail,
235 fp->_IO_save_end + least_mark,
236 -least_mark);
237 memcpy (fp->_IO_save_base + avail - least_mark,
238 fp->_IO_read_base,
239 fp->_IO_read_end - fp->_IO_read_base);
96aa2d94
RM
240 }
241 else if (needed_size > 0)
40a55d20
UD
242 memcpy (fp->_IO_save_base + avail,
243 fp->_IO_read_base + least_mark,
244 needed_size);
96aa2d94
RM
245 }
246 /* FIXME: Dubious arithmetic if pointers are NULL */
247 fp->_IO_backup_base = fp->_IO_save_base + avail;
248 /* Adjust all the streammarkers. */
249 delta = fp->_IO_read_end - fp->_IO_read_base;
250 for (mark = fp->_markers; mark != NULL; mark = mark->_next)
251 mark->_pos -= delta;
252 return 0;
253}
254
255int
40a55d20
UD
256__underflow (fp)
257 _IO_FILE *fp;
96aa2d94 258{
40a55d20
UD
259 if (_IO_in_put_mode (fp))
260 if (_IO_switch_to_get_mode (fp) == EOF)
261 return EOF;
96aa2d94 262 if (fp->_IO_read_ptr < fp->_IO_read_end)
40a55d20
UD
263 return *(unsigned char *) fp->_IO_read_ptr;
264 if (_IO_in_backup (fp))
96aa2d94 265 {
40a55d20 266 _IO_switch_to_main_get_area (fp);
96aa2d94
RM
267 if (fp->_IO_read_ptr < fp->_IO_read_end)
268 return *fp->_IO_read_ptr;
269 }
40a55d20 270 if (_IO_have_markers (fp))
96aa2d94
RM
271 {
272 if (save_for_backup (fp))
273 return EOF;
274 }
40a55d20
UD
275 else if (_IO_have_backup (fp))
276 _IO_free_backup_area (fp);
96aa2d94
RM
277 return _IO_UNDERFLOW (fp);
278}
279
280int
40a55d20
UD
281__uflow (fp)
282 _IO_FILE *fp;
96aa2d94 283{
40a55d20
UD
284 if (_IO_in_put_mode (fp))
285 if (_IO_switch_to_get_mode (fp) == EOF)
286 return EOF;
96aa2d94 287 if (fp->_IO_read_ptr < fp->_IO_read_end)
40a55d20
UD
288 return *(unsigned char *) fp->_IO_read_ptr++;
289 if (_IO_in_backup (fp))
96aa2d94 290 {
40a55d20 291 _IO_switch_to_main_get_area (fp);
96aa2d94
RM
292 if (fp->_IO_read_ptr < fp->_IO_read_end)
293 return *fp->_IO_read_ptr++;
294 }
40a55d20 295 if (_IO_have_markers (fp))
96aa2d94
RM
296 {
297 if (save_for_backup (fp))
298 return EOF;
299 }
40a55d20
UD
300 else if (_IO_have_backup (fp))
301 _IO_free_backup_area (fp);
96aa2d94
RM
302 return _IO_UFLOW (fp);
303}
304
305void
40a55d20
UD
306_IO_setb (f, b, eb, a)
307 _IO_FILE *f;
308 char *b;
309 char *eb;
310 int a;
96aa2d94
RM
311{
312 if (f->_IO_buf_base && !(f->_flags & _IO_USER_BUF))
40a55d20 313 FREE_BUF (f->_IO_buf_base, _IO_blen (f));
96aa2d94
RM
314 f->_IO_buf_base = b;
315 f->_IO_buf_end = eb;
316 if (a)
317 f->_flags &= ~_IO_USER_BUF;
318 else
319 f->_flags |= _IO_USER_BUF;
320}
321
322void
40a55d20
UD
323_IO_doallocbuf (fp)
324 _IO_FILE *fp;
96aa2d94
RM
325{
326 if (fp->_IO_buf_base)
327 return;
328 if (!(fp->_flags & _IO_UNBUFFERED))
329 if (_IO_DOALLOCATE (fp) != EOF)
330 return;
40a55d20 331 _IO_setb (fp, fp->_shortbuf, fp->_shortbuf+1, 0);
96aa2d94
RM
332}
333
334int
40a55d20
UD
335_IO_default_underflow (fp)
336 _IO_FILE *fp;
96aa2d94
RM
337{
338 return EOF;
339}
340
341int
40a55d20
UD
342_IO_default_uflow (fp)
343 _IO_FILE *fp;
96aa2d94
RM
344{
345 int ch = _IO_UNDERFLOW (fp);
346 if (ch == EOF)
347 return EOF;
40a55d20 348 return *(unsigned char *) fp->_IO_read_ptr++;
96aa2d94
RM
349}
350
351_IO_size_t
40a55d20
UD
352_IO_default_xsputn (f, data, n)
353 _IO_FILE *f;
354 const void *data;
355 _IO_size_t n;
96aa2d94 356{
40a55d20
UD
357 const char *s = (char *) data;
358 _IO_size_t more = n;
96aa2d94
RM
359 if (more <= 0)
360 return 0;
361 for (;;)
362 {
40a55d20
UD
363 /* Space available. */
364 _IO_ssize_t count = f->_IO_write_end - f->_IO_write_ptr;
96aa2d94
RM
365 if (count > 0)
366 {
a68b0d31 367 if ((_IO_size_t) count > more)
96aa2d94
RM
368 count = more;
369 if (count > 20)
370 {
40a55d20 371 memcpy (f->_IO_write_ptr, s, count);
96aa2d94
RM
372 s += count;
373 f->_IO_write_ptr += count;
374 }
375 else if (count <= 0)
376 count = 0;
377 else
378 {
40a55d20
UD
379 char *p = f->_IO_write_ptr;
380 _IO_ssize_t i;
381 for (i = count; --i >= 0; )
382 *p++ = *s++;
96aa2d94
RM
383 f->_IO_write_ptr = p;
384 }
385 more -= count;
386 }
40a55d20 387 if (more == 0 || __overflow (f, (unsigned char) *s++) == EOF)
96aa2d94
RM
388 break;
389 more--;
390 }
391 return n - more;
392}
393
394_IO_size_t
40a55d20
UD
395_IO_sgetn (fp, data, n)
396 _IO_FILE *fp;
397 void *data;
398 _IO_size_t n;
96aa2d94
RM
399{
400 /* FIXME handle putback buffer here! */
401 return _IO_XSGETN (fp, data, n);
402}
403
404_IO_size_t
40a55d20
UD
405_IO_default_xsgetn (fp, data, n)
406 _IO_FILE *fp;
407 void *data;
408 _IO_size_t n;
96aa2d94 409{
40a55d20
UD
410 _IO_size_t more = n;
411 char *s = (char*) data;
96aa2d94
RM
412 for (;;)
413 {
40a55d20
UD
414 /* Data available. */
415 _IO_ssize_t count = fp->_IO_read_end - fp->_IO_read_ptr;
96aa2d94
RM
416 if (count > 0)
417 {
a68b0d31 418 if ((_IO_size_t) count > more)
96aa2d94
RM
419 count = more;
420 if (count > 20)
421 {
40a55d20 422 memcpy (s, fp->_IO_read_ptr, count);
96aa2d94
RM
423 s += count;
424 fp->_IO_read_ptr += count;
425 }
426 else if (count <= 0)
427 count = 0;
428 else
429 {
40a55d20
UD
430 char *p = fp->_IO_read_ptr;
431 int i = (int) count;
432 while (--i >= 0)
433 *s++ = *p++;
96aa2d94
RM
434 fp->_IO_read_ptr = p;
435 }
436 more -= count;
437 }
40a55d20 438 if (more == 0 || __underflow (fp) == EOF)
96aa2d94
RM
439 break;
440 }
441 return n - more;
442}
443
40a55d20
UD
444#if 0
445/* Seems not to be needed. --drepper */
96aa2d94 446int
40a55d20
UD
447_IO_sync (fp)
448 _IO_FILE *fp;
96aa2d94
RM
449{
450 return 0;
451}
40a55d20 452#endif
96aa2d94 453
40a55d20
UD
454_IO_FILE *
455_IO_default_setbuf (fp, p, len)
456 _IO_FILE *fp;
457 char *p;
458 _IO_ssize_t len;
96aa2d94
RM
459{
460 if (_IO_SYNC (fp) == EOF)
461 return NULL;
462 if (p == NULL || len == 0)
463 {
464 fp->_flags |= _IO_UNBUFFERED;
40a55d20 465 _IO_setb (fp, fp->_shortbuf, fp->_shortbuf+1, 0);
96aa2d94
RM
466 }
467 else
468 {
469 fp->_flags &= ~_IO_UNBUFFERED;
40a55d20 470 _IO_setb (fp, p, p+len, 0);
96aa2d94
RM
471 }
472 fp->_IO_write_base = fp->_IO_write_ptr = fp->_IO_write_end = 0;
473 fp->_IO_read_base = fp->_IO_read_ptr = fp->_IO_read_end = 0;
474 return fp;
475}
476
dfd2257a 477_IO_fpos64_t
40a55d20
UD
478_IO_default_seekpos (fp, pos, mode)
479 _IO_FILE *fp;
dfd2257a 480 _IO_fpos64_t pos;
40a55d20 481 int mode;
96aa2d94 482{
40a55d20 483 return _IO_SEEKOFF (fp, _IO_pos_as_off (pos), 0, mode);
96aa2d94
RM
484}
485
486int
40a55d20
UD
487_IO_default_doallocate (fp)
488 _IO_FILE *fp;
96aa2d94 489{
f8b87ef0
UD
490 char *buf;
491
40a55d20
UD
492 ALLOC_BUF (buf, _IO_BUFSIZ, EOF);
493 _IO_setb (fp, buf, buf+_IO_BUFSIZ, 1);
96aa2d94
RM
494 return 1;
495}
496
497void
40a55d20
UD
498_IO_init (fp, flags)
499 _IO_FILE *fp;
500 int flags;
96aa2d94
RM
501{
502 fp->_flags = _IO_MAGIC|flags;
503 fp->_IO_buf_base = NULL;
504 fp->_IO_buf_end = NULL;
505 fp->_IO_read_base = NULL;
506 fp->_IO_read_ptr = NULL;
507 fp->_IO_read_end = NULL;
508 fp->_IO_write_base = NULL;
509 fp->_IO_write_ptr = NULL;
510 fp->_IO_write_end = NULL;
511 fp->_chain = NULL; /* Not necessary. */
512
513 fp->_IO_save_base = NULL;
514 fp->_IO_backup_base = NULL;
515 fp->_IO_save_end = NULL;
516 fp->_markers = NULL;
517 fp->_cur_column = 0;
7c713e28 518#ifdef _IO_MTSAFE_IO
df4ef2ab 519 _IO_lock_init (*fp->_lock);
7c713e28 520#endif
96aa2d94
RM
521}
522
523int
40a55d20
UD
524_IO_default_sync (fp)
525 _IO_FILE *fp;
96aa2d94
RM
526{
527 return 0;
528}
529
530/* The way the C++ classes are mapped into the C functions in the
531 current implementation, this function can get called twice! */
532
533void
40a55d20
UD
534_IO_default_finish (fp, dummy)
535 _IO_FILE *fp;
536 int dummy;
96aa2d94
RM
537{
538 struct _IO_marker *mark;
539 if (fp->_IO_buf_base && !(fp->_flags & _IO_USER_BUF))
540 {
40a55d20 541 FREE_BUF (fp->_IO_buf_base, _IO_blen (fp));
96aa2d94
RM
542 fp->_IO_buf_base = fp->_IO_buf_end = NULL;
543 }
544
545 for (mark = fp->_markers; mark != NULL; mark = mark->_next)
546 mark->_sbuf = NULL;
547
548 if (fp->_IO_save_base)
549 {
550 free (fp->_IO_save_base);
551 fp->_IO_save_base = NULL;
552 }
553
7c713e28 554#ifdef _IO_MTSAFE_IO
68dbb3a6 555 _IO_lock_fini (*fp->_lock);
7c713e28 556#endif
adfa2078 557
40a55d20 558 _IO_un_link (fp);
96aa2d94
RM
559}
560
dfd2257a 561_IO_fpos64_t
40a55d20
UD
562_IO_default_seekoff (fp, offset, dir, mode)
563 _IO_FILE *fp;
dfd2257a 564 _IO_off64_t offset;
40a55d20
UD
565 int dir;
566 int mode;
96aa2d94
RM
567{
568 return _IO_pos_BAD;
569}
570
571int
40a55d20
UD
572_IO_sputbackc (fp, c)
573 _IO_FILE *fp;
574 int c;
96aa2d94 575{
19bc17a9 576 int result;
adfa2078 577
96aa2d94
RM
578 if (fp->_IO_read_ptr > fp->_IO_read_base
579 && (unsigned char)fp->_IO_read_ptr[-1] == (unsigned char)c)
580 {
581 fp->_IO_read_ptr--;
40a55d20 582 result = (unsigned char) c;
96aa2d94 583 }
19bc17a9
RM
584 else
585 result = _IO_PBACKFAIL (fp, c);
586
587 if (result != EOF)
588 fp->_flags &= ~_IO_EOF_SEEN;
589
590 return result;
96aa2d94
RM
591}
592
593int
40a55d20
UD
594_IO_sungetc (fp)
595 _IO_FILE *fp;
96aa2d94 596{
19bc17a9 597 int result;
adfa2078 598
96aa2d94
RM
599 if (fp->_IO_read_ptr > fp->_IO_read_base)
600 {
601 fp->_IO_read_ptr--;
40a55d20 602 result = (unsigned char) *fp->_IO_read_ptr;
96aa2d94
RM
603 }
604 else
19bc17a9
RM
605 result = _IO_PBACKFAIL (fp, EOF);
606
607 if (result != EOF)
608 fp->_flags &= ~_IO_EOF_SEEN;
609
610 return result;
96aa2d94
RM
611}
612
613#if 0 /* Work in progress */
40a55d20
UD
614/* Seems not to be needed. */
615#if 0
96aa2d94 616void
40a55d20
UD
617_IO_set_column (fp, c)
618 _IO_FILE *fp;
619 int c;
96aa2d94
RM
620{
621 if (c == -1)
622 fp->_column = -1;
623 else
624 fp->_column = c - (fp->_IO_write_ptr - fp->_IO_write_base);
625}
626#else
627int
40a55d20
UD
628_IO_set_column (fp, i)
629 _IO_FILE *fp;
630 int i;
96aa2d94 631{
40a55d20 632 fp->_cur_column = i + 1;
96aa2d94
RM
633 return 0;
634}
635#endif
40a55d20 636#endif
96aa2d94
RM
637
638
639unsigned
40a55d20
UD
640_IO_adjust_column (start, line, count)
641 unsigned start;
642 const char *line;
643 int count;
96aa2d94 644{
40a55d20 645 const char *ptr = line + count;
96aa2d94
RM
646 while (ptr > line)
647 if (*--ptr == '\n')
648 return line + count - ptr - 1;
649 return start + count;
650}
651
40a55d20
UD
652#if 0
653/* Seems not to be needed. --drepper */
96aa2d94 654int
40a55d20
UD
655_IO_get_column (fp)
656 _IO_FILE *fp;
96aa2d94 657{
adfa2078 658 if (fp->_cur_column)
40a55d20 659 return _IO_adjust_column (fp->_cur_column - 1,
96aa2d94
RM
660 fp->_IO_write_base,
661 fp->_IO_write_ptr - fp->_IO_write_base);
662 return -1;
663}
40a55d20 664#endif
96aa2d94
RM
665
666int
40a55d20 667_IO_flush_all ()
96aa2d94
RM
668{
669 int result = 0;
670 _IO_FILE *fp;
671 for (fp = _IO_list_all; fp != NULL; fp = fp->_chain)
672 if (fp->_IO_write_ptr > fp->_IO_write_base
673 && _IO_OVERFLOW (fp, EOF) == EOF)
674 result = EOF;
675 return result;
676}
677
678void
40a55d20 679_IO_flush_all_linebuffered ()
96aa2d94
RM
680{
681 _IO_FILE *fp;
682 for (fp = _IO_list_all; fp != NULL; fp = fp->_chain)
63551311 683 if ((fp->_flags & _IO_NO_WRITES) == 0 && fp->_flags & _IO_LINE_BUF)
96aa2d94
RM
684 _IO_OVERFLOW (fp, EOF);
685}
686
40a55d20
UD
687static void _IO_unbuffer_all __P ((void));
688
689static void
690_IO_unbuffer_all ()
96aa2d94
RM
691{
692 _IO_FILE *fp;
693 for (fp = _IO_list_all; fp != NULL; fp = fp->_chain)
694 if (! (fp->_flags & _IO_UNBUFFERED))
695 _IO_SETBUF (fp, NULL, 0);
696}
697
698void
40a55d20 699_IO_cleanup ()
96aa2d94
RM
700{
701 _IO_flush_all ();
702
703 /* We currently don't have a reliable mechanism for making sure that
704 C++ static destructors are executed in the correct order.
6d52618b 705 So it is possible that other static destructors might want to
96aa2d94
RM
706 write to cout - and they're supposed to be able to do so.
707
adfa2078 708 The following will make the standard streambufs be unbuffered,
96aa2d94
RM
709 which forces any output from late destructors to be written out. */
710 _IO_unbuffer_all ();
711}
712
f2ea0f5b
UD
713_IO_FILE *_IO_list_all = &_IO_stderr_.plus.file;
714
96aa2d94 715void
40a55d20
UD
716_IO_init_marker (marker, fp)
717 struct _IO_marker *marker;
718 _IO_FILE *fp;
96aa2d94
RM
719{
720 marker->_sbuf = fp;
40a55d20
UD
721 if (_IO_in_put_mode (fp))
722 _IO_switch_to_get_mode (fp);
723 if (_IO_in_backup (fp))
96aa2d94
RM
724 marker->_pos = fp->_IO_read_ptr - fp->_IO_read_end;
725 else
726 marker->_pos = fp->_IO_read_ptr - fp->_IO_read_base;
adfa2078 727
96aa2d94
RM
728 /* Should perhaps sort the chain? */
729 marker->_next = fp->_markers;
730 fp->_markers = marker;
731}
732
733void
40a55d20
UD
734_IO_remove_marker (marker)
735 struct _IO_marker *marker;
96aa2d94
RM
736{
737 /* Unlink from sb's chain. */
40a55d20 738 struct _IO_marker **ptr = &marker->_sbuf->_markers;
96aa2d94
RM
739 for (; ; ptr = &(*ptr)->_next)
740 {
741 if (*ptr == NULL)
742 break;
743 else if (*ptr == marker)
744 {
745 *ptr = marker->_next;
746 return;
747 }
748 }
749#if 0
750 if _sbuf has a backup area that is no longer needed, should we delete
751 it now, or wait until the next underflow?
752#endif
753}
754
755#define BAD_DELTA EOF
756
757int
40a55d20
UD
758_IO_marker_difference (mark1, mark2)
759 struct _IO_marker *mark1;
760 struct _IO_marker *mark2;
96aa2d94
RM
761{
762 return mark1->_pos - mark2->_pos;
763}
764
6d52618b 765/* Return difference between MARK and current position of MARK's stream. */
96aa2d94 766int
40a55d20
UD
767_IO_marker_delta (mark)
768 struct _IO_marker *mark;
96aa2d94
RM
769{
770 int cur_pos;
771 if (mark->_sbuf == NULL)
772 return BAD_DELTA;
40a55d20 773 if (_IO_in_backup (mark->_sbuf))
96aa2d94
RM
774 cur_pos = mark->_sbuf->_IO_read_ptr - mark->_sbuf->_IO_read_end;
775 else
776 cur_pos = mark->_sbuf->_IO_read_ptr - mark->_sbuf->_IO_read_base;
777 return mark->_pos - cur_pos;
778}
779
780int
40a55d20
UD
781_IO_seekmark (fp, mark, delta)
782 _IO_FILE *fp;
783 struct _IO_marker *mark;
784 int delta;
96aa2d94
RM
785{
786 if (mark->_sbuf != fp)
787 return EOF;
788 if (mark->_pos >= 0)
789 {
40a55d20
UD
790 if (_IO_in_backup (fp))
791 _IO_switch_to_main_get_area (fp);
96aa2d94
RM
792 fp->_IO_read_ptr = fp->_IO_read_base + mark->_pos;
793 }
794 else
795 {
40a55d20
UD
796 if (!_IO_in_backup (fp))
797 _IO_switch_to_backup_area (fp);
96aa2d94
RM
798 fp->_IO_read_ptr = fp->_IO_read_end + mark->_pos;
799 }
800 return 0;
801}
802
803void
40a55d20
UD
804_IO_unsave_markers (fp)
805 _IO_FILE *fp;
96aa2d94 806{
40a55d20 807 struct _IO_marker *mark = fp->_markers;
96aa2d94
RM
808 if (mark)
809 {
810#ifdef TODO
40a55d20 811 streampos offset = seekoff (0, ios::cur, ios::in);
96aa2d94
RM
812 if (offset != EOF)
813 {
40a55d20 814 offset += eGptr () - Gbase ();
96aa2d94 815 for ( ; mark != NULL; mark = mark->_next)
40a55d20 816 mark->set_streampos (mark->_pos + offset);
96aa2d94
RM
817 }
818 else
819 {
820 for ( ; mark != NULL; mark = mark->_next)
40a55d20 821 mark->set_streampos (EOF);
96aa2d94
RM
822 }
823#endif
824 fp->_markers = 0;
825 }
826
40a55d20
UD
827 if (_IO_have_backup (fp))
828 _IO_free_backup_area (fp);
96aa2d94
RM
829}
830
40a55d20
UD
831#if 0
832/* Seems not to be needed. --drepper */
96aa2d94 833int
40a55d20
UD
834_IO_nobackup_pbackfail (fp, c)
835 _IO_FILE *fp;
836 int c;
96aa2d94
RM
837{
838 if (fp->_IO_read_ptr > fp->_IO_read_base)
839 fp->_IO_read_ptr--;
840 if (c != EOF && *fp->_IO_read_ptr != c)
841 *fp->_IO_read_ptr = c;
40a55d20 842 return (unsigned char) c;
96aa2d94 843}
40a55d20 844#endif
96aa2d94
RM
845
846int
40a55d20
UD
847_IO_default_pbackfail (fp, c)
848 _IO_FILE *fp;
849 int c;
96aa2d94
RM
850{
851 if (fp->_IO_read_ptr <= fp->_IO_read_base)
40a55d20
UD
852 {
853 /* Need to handle a filebuf in write mode (switch to read mode). FIXME!*/
854 if (_IO_have_backup (fp) && !_IO_in_backup (fp))
855 _IO_switch_to_backup_area (fp);
856
857 if (!_IO_have_backup (fp))
858 {
859 /* No backup buffer: allocate one. */
860 /* Use nshort buffer, if unused? (probably not) FIXME */
861 int backup_size = 128;
862 char *bbuf = (char *) malloc (backup_size);
863 if (bbuf == NULL)
864 return EOF;
865 fp->_IO_save_base = bbuf;
866 fp->_IO_save_end = fp->_IO_save_base + backup_size;
867 fp->_IO_backup_base = fp->_IO_save_end;
868 _IO_switch_to_backup_area (fp);
869 }
870 else if (fp->_IO_read_ptr <= fp->_IO_read_base)
871 {
872 /* Increase size of existing backup buffer. */
873 _IO_size_t new_size;
874 _IO_size_t old_size = fp->_IO_read_end - fp->_IO_read_base;
875 char *new_buf;
876 new_size = 2 * old_size;
877 new_buf = (char *) malloc (new_size);
878 if (new_buf == NULL)
879 return EOF;
880 memcpy (new_buf + (new_size - old_size), fp->_IO_read_base,
881 old_size);
882 free (fp->_IO_read_base);
883 _IO_setg (fp, new_buf, new_buf + (new_size - old_size),
884 new_buf + new_size);
885 fp->_IO_backup_base = fp->_IO_read_ptr;
886 }
887 }
888 --fp->_IO_read_ptr;
96aa2d94
RM
889 if (c != EOF && *fp->_IO_read_ptr != c)
890 *fp->_IO_read_ptr = c;
40a55d20 891 return (unsigned char) *fp->_IO_read_ptr;
96aa2d94
RM
892}
893
dfd2257a 894_IO_fpos64_t
40a55d20
UD
895_IO_default_seek (fp, offset, dir)
896 _IO_FILE *fp;
dfd2257a 897 _IO_off64_t offset;
40a55d20 898 int dir;
96aa2d94
RM
899{
900 return _IO_pos_BAD;
901}
902
903int
40a55d20
UD
904_IO_default_stat (fp, st)
905 _IO_FILE *fp;
906 void* st;
96aa2d94
RM
907{
908 return EOF;
909}
910
911_IO_ssize_t
40a55d20
UD
912_IO_default_read (fp, data, n)
913 _IO_FILE* fp;
914 void *data;
915 _IO_ssize_t n;
96aa2d94
RM
916{
917 return -1;
918}
919
920_IO_ssize_t
40a55d20
UD
921_IO_default_write (fp, data, n)
922 _IO_FILE *fp;
923 const void *data;
924 _IO_ssize_t n;
96aa2d94
RM
925{
926 return 0;
927}
928
dfd2257a
UD
929int
930_IO_default_showmanyc (fp)
931 _IO_FILE *fp;
932{
933 return -1;
934}
935
936void
937_IO_default_imbue (fp, locale)
938 _IO_FILE *fp;
939 void *locale;
940{
941}
942
96aa2d94
RM
943
944#ifdef TODO
945#if defined(linux)
946#define IO_CLEANUP ;
947#endif
948
949#ifdef IO_CLEANUP
950 IO_CLEANUP
951#else
952struct __io_defs {
953 __io_defs() { }
40a55d20 954 ~__io_defs() { _IO_cleanup (); }
adfa2078 955};
96aa2d94
RM
956__io_defs io_defs__;
957#endif
958
959#endif /* TODO */
adfa2078
UD
960
961#ifdef weak_alias
962weak_alias (_IO_cleanup, _cleanup)
963#endif
f65fd747
UD
964
965#ifdef text_set_element
966text_set_element(__libc_atexit, _cleanup);
967#endif
This page took 0.144809 seconds and 5 git commands to generate.