[Ada] Re-implement `info tasks' command using ui-out
[deliverable/binutils-gdb.git] / gdb / ui-file.c
CommitLineData
d9fcf2fb 1/* UI_FILE - a generic STDIO like output stream.
349c5d5f 2
7b6bb8da 3 Copyright (C) 1999, 2000, 2001, 2002, 2007, 2008, 2009, 2010, 2011
9b254dd1 4 Free Software Foundation, Inc.
d9fcf2fb
JM
5
6 This file is part of GDB.
7
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
a9762ec7 10 the Free Software Foundation; either version 3 of the License, or
d9fcf2fb
JM
11 (at your option) any later version.
12
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
a9762ec7 19 along with this program. If not, see <http://www.gnu.org/licenses/>. */
d9fcf2fb 20
581e13c1 21/* Implement the ``struct ui_file'' object. */
d9fcf2fb
JM
22
23#include "defs.h"
24#include "ui-file.h"
94af9270 25#include "gdb_obstack.h"
1d1358b6 26#include "gdb_string.h"
ad960ed2 27#include "gdb_select.h"
d9fcf2fb 28
449092f6
CV
29#include <errno.h>
30
d9fcf2fb
JM
31static ui_file_isatty_ftype null_file_isatty;
32static ui_file_write_ftype null_file_write;
01124a23 33static ui_file_write_ftype null_file_write_async_safe;
d9fcf2fb 34static ui_file_fputs_ftype null_file_fputs;
449092f6 35static ui_file_read_ftype null_file_read;
d9fcf2fb
JM
36static ui_file_flush_ftype null_file_flush;
37static ui_file_delete_ftype null_file_delete;
38static ui_file_rewind_ftype null_file_rewind;
39static ui_file_put_ftype null_file_put;
40
41struct ui_file
42 {
43 int *magic;
44 ui_file_flush_ftype *to_flush;
45 ui_file_write_ftype *to_write;
01124a23 46 ui_file_write_async_safe_ftype *to_write_async_safe;
d9fcf2fb 47 ui_file_fputs_ftype *to_fputs;
449092f6 48 ui_file_read_ftype *to_read;
d9fcf2fb
JM
49 ui_file_delete_ftype *to_delete;
50 ui_file_isatty_ftype *to_isatty;
51 ui_file_rewind_ftype *to_rewind;
52 ui_file_put_ftype *to_put;
53 void *to_data;
54 };
55int ui_file_magic;
56
57struct ui_file *
fba45db2 58ui_file_new (void)
d9fcf2fb
JM
59{
60 struct ui_file *file = xmalloc (sizeof (struct ui_file));
5d502164 61
d9fcf2fb
JM
62 file->magic = &ui_file_magic;
63 set_ui_file_data (file, NULL, null_file_delete);
64 set_ui_file_flush (file, null_file_flush);
65 set_ui_file_write (file, null_file_write);
01124a23 66 set_ui_file_write_async_safe (file, null_file_write_async_safe);
d9fcf2fb 67 set_ui_file_fputs (file, null_file_fputs);
449092f6 68 set_ui_file_read (file, null_file_read);
d9fcf2fb
JM
69 set_ui_file_isatty (file, null_file_isatty);
70 set_ui_file_rewind (file, null_file_rewind);
71 set_ui_file_put (file, null_file_put);
72 return file;
73}
74
75void
fba45db2 76ui_file_delete (struct ui_file *file)
d9fcf2fb
JM
77{
78 file->to_delete (file);
b8c9b27d 79 xfree (file);
d9fcf2fb
JM
80}
81
82static int
fba45db2 83null_file_isatty (struct ui_file *file)
d9fcf2fb
JM
84{
85 return 0;
86}
87
88static void
fba45db2 89null_file_rewind (struct ui_file *file)
d9fcf2fb
JM
90{
91 return;
92}
93
94static void
95null_file_put (struct ui_file *file,
96 ui_file_put_method_ftype *write,
97 void *dest)
98{
99 return;
100}
101
102static void
fba45db2 103null_file_flush (struct ui_file *file)
d9fcf2fb
JM
104{
105 return;
106}
107
108static void
109null_file_write (struct ui_file *file,
110 const char *buf,
111 long sizeof_buf)
112{
113 if (file->to_fputs == null_file_fputs)
581e13c1
MS
114 /* Both the write and fputs methods are null. Discard the
115 request. */
d9fcf2fb
JM
116 return;
117 else
118 {
119 /* The fputs method isn't null, slowly pass the write request
120 onto that. FYI, this isn't as bad as it may look - the
121 current (as of 1999-11-07) printf_* function calls fputc and
122 fputc does exactly the below. By having a write function it
123 is possible to clean up that code. */
124 int i;
125 char b[2];
5d502164 126
d9fcf2fb
JM
127 b[1] = '\0';
128 for (i = 0; i < sizeof_buf; i++)
129 {
130 b[0] = buf[i];
131 file->to_fputs (b, file);
132 }
133 return;
134 }
135}
136
449092f6
CV
137static long
138null_file_read (struct ui_file *file,
139 char *buf,
140 long sizeof_buf)
141{
142 errno = EBADF;
143 return 0;
144}
145
d9fcf2fb 146static void
fba45db2 147null_file_fputs (const char *buf, struct ui_file *file)
d9fcf2fb
JM
148{
149 if (file->to_write == null_file_write)
581e13c1
MS
150 /* Both the write and fputs methods are null. Discard the
151 request. */
d9fcf2fb
JM
152 return;
153 else
154 {
581e13c1 155 /* The write method was implemented, use that. */
d9fcf2fb
JM
156 file->to_write (file, buf, strlen (buf));
157 }
158}
159
01124a23
DE
160static void
161null_file_write_async_safe (struct ui_file *file,
162 const char *buf,
163 long sizeof_buf)
164{
165 return;
166}
167
d9fcf2fb 168static void
fba45db2 169null_file_delete (struct ui_file *file)
d9fcf2fb
JM
170{
171 return;
172}
173
174void *
fba45db2 175ui_file_data (struct ui_file *file)
d9fcf2fb
JM
176{
177 if (file->magic != &ui_file_magic)
8e65ff28 178 internal_error (__FILE__, __LINE__,
e2e0b3e5 179 _("ui_file_data: bad magic number"));
d9fcf2fb
JM
180 return file->to_data;
181}
182
183void
fba45db2 184gdb_flush (struct ui_file *file)
d9fcf2fb
JM
185{
186 file->to_flush (file);
187}
188
189int
fba45db2 190ui_file_isatty (struct ui_file *file)
d9fcf2fb
JM
191{
192 return file->to_isatty (file);
193}
194
195void
fba45db2 196ui_file_rewind (struct ui_file *file)
d9fcf2fb
JM
197{
198 file->to_rewind (file);
199}
200
201void
202ui_file_put (struct ui_file *file,
203 ui_file_put_method_ftype *write,
204 void *dest)
205{
206 file->to_put (file, write, dest);
207}
208
209void
210ui_file_write (struct ui_file *file,
211 const char *buf,
212 long length_buf)
213{
214 file->to_write (file, buf, length_buf);
215}
216
01124a23
DE
217void
218ui_file_write_async_safe (struct ui_file *file,
219 const char *buf,
220 long length_buf)
221{
222 file->to_write_async_safe (file, buf, length_buf);
223}
224
449092f6
CV
225long
226ui_file_read (struct ui_file *file, char *buf, long length_buf)
227{
228 return file->to_read (file, buf, length_buf);
229}
230
d9fcf2fb 231void
fba45db2 232fputs_unfiltered (const char *buf, struct ui_file *file)
d9fcf2fb
JM
233{
234 file->to_fputs (buf, file);
235}
236
237void
fba45db2 238set_ui_file_flush (struct ui_file *file, ui_file_flush_ftype *flush)
d9fcf2fb
JM
239{
240 file->to_flush = flush;
241}
242
243void
fba45db2 244set_ui_file_isatty (struct ui_file *file, ui_file_isatty_ftype *isatty)
d9fcf2fb
JM
245{
246 file->to_isatty = isatty;
247}
248
249void
fba45db2 250set_ui_file_rewind (struct ui_file *file, ui_file_rewind_ftype *rewind)
d9fcf2fb
JM
251{
252 file->to_rewind = rewind;
253}
254
255void
fba45db2 256set_ui_file_put (struct ui_file *file, ui_file_put_ftype *put)
d9fcf2fb
JM
257{
258 file->to_put = put;
259}
260
261void
262set_ui_file_write (struct ui_file *file,
263 ui_file_write_ftype *write)
264{
265 file->to_write = write;
266}
267
01124a23
DE
268void
269set_ui_file_write_async_safe (struct ui_file *file,
270 ui_file_write_async_safe_ftype *write_async_safe)
271{
272 file->to_write_async_safe = write_async_safe;
273}
274
449092f6
CV
275void
276set_ui_file_read (struct ui_file *file, ui_file_read_ftype *read)
277{
278 file->to_read = read;
279}
280
d9fcf2fb 281void
fba45db2 282set_ui_file_fputs (struct ui_file *file, ui_file_fputs_ftype *fputs)
d9fcf2fb
JM
283{
284 file->to_fputs = fputs;
285}
286
287void
fba45db2
KB
288set_ui_file_data (struct ui_file *file, void *data,
289 ui_file_delete_ftype *delete)
d9fcf2fb
JM
290{
291 file->to_data = data;
292 file->to_delete = delete;
293}
294
295/* ui_file utility function for converting a ``struct ui_file'' into
581e13c1 296 a memory buffer. */
d9fcf2fb
JM
297
298struct accumulated_ui_file
299{
300 char *buffer;
301 long length;
302};
303
304static void
305do_ui_file_xstrdup (void *context, const char *buffer, long length)
306{
307 struct accumulated_ui_file *acc = context;
5d502164 308
d9fcf2fb
JM
309 if (acc->buffer == NULL)
310 acc->buffer = xmalloc (length + 1);
311 else
312 acc->buffer = xrealloc (acc->buffer, acc->length + length + 1);
313 memcpy (acc->buffer + acc->length, buffer, length);
314 acc->length += length;
315 acc->buffer[acc->length] = '\0';
316}
317
318char *
759ef836 319ui_file_xstrdup (struct ui_file *file, long *length)
d9fcf2fb
JM
320{
321 struct accumulated_ui_file acc;
5d502164 322
d9fcf2fb
JM
323 acc.buffer = NULL;
324 acc.length = 0;
325 ui_file_put (file, do_ui_file_xstrdup, &acc);
326 if (acc.buffer == NULL)
327 acc.buffer = xstrdup ("");
759ef836
PA
328 if (length != NULL)
329 *length = acc.length;
d9fcf2fb
JM
330 return acc.buffer;
331}
94af9270
KS
332
333static void
334do_ui_file_obsavestring (void *context, const char *buffer, long length)
335{
336 struct obstack *obstack = (struct obstack *) context;
5d502164 337
94af9270
KS
338 obstack_grow (obstack, buffer, length);
339}
340
341char *
342ui_file_obsavestring (struct ui_file *file, struct obstack *obstack,
343 long *length)
344{
345 ui_file_put (file, do_ui_file_obsavestring, obstack);
346 *length = obstack_object_size (obstack);
347 obstack_1grow (obstack, '\0');
348 return obstack_finish (obstack);
349}
d9fcf2fb
JM
350\f
351/* A pure memory based ``struct ui_file'' that can be used an output
581e13c1
MS
352 buffer. The buffers accumulated contents are available via
353 ui_file_put(). */
d9fcf2fb
JM
354
355struct mem_file
356 {
357 int *magic;
358 char *buffer;
359 int sizeof_buffer;
360 int length_buffer;
361 };
362
363static ui_file_rewind_ftype mem_file_rewind;
364static ui_file_put_ftype mem_file_put;
365static ui_file_write_ftype mem_file_write;
366static ui_file_delete_ftype mem_file_delete;
a14ed312 367static struct ui_file *mem_file_new (void);
d9fcf2fb
JM
368static int mem_file_magic;
369
370static struct ui_file *
371mem_file_new (void)
372{
373 struct mem_file *stream = XMALLOC (struct mem_file);
374 struct ui_file *file = ui_file_new ();
5d502164 375
d9fcf2fb
JM
376 set_ui_file_data (file, stream, mem_file_delete);
377 set_ui_file_rewind (file, mem_file_rewind);
378 set_ui_file_put (file, mem_file_put);
379 set_ui_file_write (file, mem_file_write);
380 stream->magic = &mem_file_magic;
381 stream->buffer = NULL;
382 stream->sizeof_buffer = 0;
383 stream->length_buffer = 0;
384 return file;
385}
386
387static void
388mem_file_delete (struct ui_file *file)
389{
390 struct mem_file *stream = ui_file_data (file);
5d502164 391
d9fcf2fb 392 if (stream->magic != &mem_file_magic)
8e65ff28 393 internal_error (__FILE__, __LINE__,
e2e0b3e5 394 _("mem_file_delete: bad magic number"));
d9fcf2fb 395 if (stream->buffer != NULL)
b8c9b27d
KB
396 xfree (stream->buffer);
397 xfree (stream);
d9fcf2fb
JM
398}
399
400struct ui_file *
401mem_fileopen (void)
402{
403 return mem_file_new ();
404}
405
406static void
407mem_file_rewind (struct ui_file *file)
408{
409 struct mem_file *stream = ui_file_data (file);
5d502164 410
d9fcf2fb 411 if (stream->magic != &mem_file_magic)
8e65ff28 412 internal_error (__FILE__, __LINE__,
e2e0b3e5 413 _("mem_file_rewind: bad magic number"));
d9fcf2fb
JM
414 stream->length_buffer = 0;
415}
416
417static void
418mem_file_put (struct ui_file *file,
419 ui_file_put_method_ftype *write,
420 void *dest)
421{
422 struct mem_file *stream = ui_file_data (file);
5d502164 423
d9fcf2fb 424 if (stream->magic != &mem_file_magic)
8e65ff28 425 internal_error (__FILE__, __LINE__,
e2e0b3e5 426 _("mem_file_put: bad magic number"));
d9fcf2fb
JM
427 if (stream->length_buffer > 0)
428 write (dest, stream->buffer, stream->length_buffer);
429}
430
431void
432mem_file_write (struct ui_file *file,
433 const char *buffer,
434 long length_buffer)
435{
436 struct mem_file *stream = ui_file_data (file);
5d502164 437
d9fcf2fb 438 if (stream->magic != &mem_file_magic)
8e65ff28 439 internal_error (__FILE__, __LINE__,
e2e0b3e5 440 _("mem_file_write: bad magic number"));
d9fcf2fb
JM
441 if (stream->buffer == NULL)
442 {
443 stream->length_buffer = length_buffer;
444 stream->sizeof_buffer = length_buffer;
445 stream->buffer = xmalloc (stream->sizeof_buffer);
446 memcpy (stream->buffer, buffer, length_buffer);
447 }
448 else
449 {
450 int new_length = stream->length_buffer + length_buffer;
5d502164 451
d9fcf2fb
JM
452 if (new_length >= stream->sizeof_buffer)
453 {
454 stream->sizeof_buffer = new_length;
455 stream->buffer = xrealloc (stream->buffer, stream->sizeof_buffer);
456 }
457 memcpy (stream->buffer + stream->length_buffer, buffer, length_buffer);
458 stream->length_buffer = new_length;
459 }
460}
461\f
462/* ``struct ui_file'' implementation that maps directly onto
581e13c1 463 <stdio.h>'s FILE. */
d9fcf2fb
JM
464
465static ui_file_write_ftype stdio_file_write;
01124a23 466static ui_file_write_async_safe_ftype stdio_file_write_async_safe;
d9fcf2fb 467static ui_file_fputs_ftype stdio_file_fputs;
449092f6 468static ui_file_read_ftype stdio_file_read;
d9fcf2fb
JM
469static ui_file_isatty_ftype stdio_file_isatty;
470static ui_file_delete_ftype stdio_file_delete;
3e43a32a 471static struct ui_file *stdio_file_new (FILE *file, int close_p);
d9fcf2fb
JM
472static ui_file_flush_ftype stdio_file_flush;
473
474static int stdio_file_magic;
475
476struct stdio_file
477 {
478 int *magic;
479 FILE *file;
01124a23
DE
480 /* The associated file descriptor is extracted ahead of time for
481 stdio_file_write_async_safe's benefit, in case fileno isn't async-safe. */
482 int fd;
d9fcf2fb
JM
483 int close_p;
484 };
485
486static struct ui_file *
fba45db2 487stdio_file_new (FILE *file, int close_p)
d9fcf2fb
JM
488{
489 struct ui_file *ui_file = ui_file_new ();
490 struct stdio_file *stdio = xmalloc (sizeof (struct stdio_file));
5d502164 491
d9fcf2fb
JM
492 stdio->magic = &stdio_file_magic;
493 stdio->file = file;
01124a23 494 stdio->fd = fileno (file);
d9fcf2fb
JM
495 stdio->close_p = close_p;
496 set_ui_file_data (ui_file, stdio, stdio_file_delete);
497 set_ui_file_flush (ui_file, stdio_file_flush);
498 set_ui_file_write (ui_file, stdio_file_write);
01124a23 499 set_ui_file_write_async_safe (ui_file, stdio_file_write_async_safe);
d9fcf2fb 500 set_ui_file_fputs (ui_file, stdio_file_fputs);
449092f6 501 set_ui_file_read (ui_file, stdio_file_read);
d9fcf2fb
JM
502 set_ui_file_isatty (ui_file, stdio_file_isatty);
503 return ui_file;
504}
505
506static void
fba45db2 507stdio_file_delete (struct ui_file *file)
d9fcf2fb
JM
508{
509 struct stdio_file *stdio = ui_file_data (file);
5d502164 510
d9fcf2fb 511 if (stdio->magic != &stdio_file_magic)
8e65ff28 512 internal_error (__FILE__, __LINE__,
e2e0b3e5 513 _("stdio_file_delete: bad magic number"));
d9fcf2fb
JM
514 if (stdio->close_p)
515 {
516 fclose (stdio->file);
517 }
b8c9b27d 518 xfree (stdio);
d9fcf2fb
JM
519}
520
521static void
fba45db2 522stdio_file_flush (struct ui_file *file)
d9fcf2fb
JM
523{
524 struct stdio_file *stdio = ui_file_data (file);
5d502164 525
d9fcf2fb 526 if (stdio->magic != &stdio_file_magic)
8e65ff28 527 internal_error (__FILE__, __LINE__,
e2e0b3e5 528 _("stdio_file_flush: bad magic number"));
d9fcf2fb
JM
529 fflush (stdio->file);
530}
531
449092f6
CV
532static long
533stdio_file_read (struct ui_file *file, char *buf, long length_buf)
534{
535 struct stdio_file *stdio = ui_file_data (file);
5d502164 536
449092f6
CV
537 if (stdio->magic != &stdio_file_magic)
538 internal_error (__FILE__, __LINE__,
e2e0b3e5 539 _("stdio_file_read: bad magic number"));
ad960ed2
DJ
540
541 /* For the benefit of Windows, call gdb_select before reading from
542 the file. Wait until at least one byte of data is available.
543 Control-C can interrupt gdb_select, but not read. */
544 {
ad960ed2
DJ
545 fd_set readfds;
546 FD_ZERO (&readfds);
01124a23
DE
547 FD_SET (stdio->fd, &readfds);
548 if (gdb_select (stdio->fd + 1, &readfds, NULL, NULL, NULL) == -1)
ad960ed2
DJ
549 return -1;
550 }
551
01124a23 552 return read (stdio->fd, buf, length_buf);
449092f6
CV
553}
554
d9fcf2fb
JM
555static void
556stdio_file_write (struct ui_file *file, const char *buf, long length_buf)
557{
558 struct stdio_file *stdio = ui_file_data (file);
5d502164 559
d9fcf2fb 560 if (stdio->magic != &stdio_file_magic)
8e65ff28 561 internal_error (__FILE__, __LINE__,
e2e0b3e5 562 _("stdio_file_write: bad magic number"));
bf1d7d9c
JB
563 /* Calling error crashes when we are called from the exception framework. */
564 if (fwrite (buf, length_buf, 1, stdio->file))
565 ;
d9fcf2fb
JM
566}
567
01124a23
DE
568static void
569stdio_file_write_async_safe (struct ui_file *file,
570 const char *buf, long length_buf)
571{
572 struct stdio_file *stdio = ui_file_data (file);
573
574 if (stdio->magic != &stdio_file_magic)
575 {
576 /* gettext isn't necessarily async safe, so we can't use _("error message") here.
577 We could extract the correct translation ahead of time, but this is an extremely
578 rare event, and one of the other stdio_file_* routines will presumably catch
579 the problem anyway. For now keep it simple and ignore the error here. */
580 return;
581 }
582
9f7bc587
DE
583 /* This is written the way it is to avoid a warning from gcc about not using the
584 result of write (since it can be declared with attribute warn_unused_result).
585 Alas casting to void doesn't work for this. */
093cee7d
HZ
586 if (write (stdio->fd, buf, length_buf))
587 ;
01124a23
DE
588}
589
d9fcf2fb 590static void
fba45db2 591stdio_file_fputs (const char *linebuffer, struct ui_file *file)
d9fcf2fb
JM
592{
593 struct stdio_file *stdio = ui_file_data (file);
5d502164 594
d9fcf2fb 595 if (stdio->magic != &stdio_file_magic)
8e65ff28 596 internal_error (__FILE__, __LINE__,
e2e0b3e5 597 _("stdio_file_fputs: bad magic number"));
bf1d7d9c
JB
598 /* Calling error crashes when we are called from the exception framework. */
599 if (fputs (linebuffer, stdio->file))
600 ;
d9fcf2fb
JM
601}
602
603static int
fba45db2 604stdio_file_isatty (struct ui_file *file)
d9fcf2fb
JM
605{
606 struct stdio_file *stdio = ui_file_data (file);
5d502164 607
d9fcf2fb 608 if (stdio->magic != &stdio_file_magic)
8e65ff28 609 internal_error (__FILE__, __LINE__,
e2e0b3e5 610 _("stdio_file_isatty: bad magic number"));
01124a23 611 return (isatty (stdio->fd));
d9fcf2fb
JM
612}
613
581e13c1 614/* Like fdopen(). Create a ui_file from a previously opened FILE. */
d9fcf2fb
JM
615
616struct ui_file *
fba45db2 617stdio_fileopen (FILE *file)
d9fcf2fb
JM
618{
619 return stdio_file_new (file, 0);
620}
621
622struct ui_file *
fba45db2 623gdb_fopen (char *name, char *mode)
d9fcf2fb
JM
624{
625 FILE *f = fopen (name, mode);
5d502164 626
d9fcf2fb
JM
627 if (f == NULL)
628 return NULL;
629 return stdio_file_new (f, 1);
630}
e4c242d9
DJ
631
632/* ``struct ui_file'' implementation that maps onto two ui-file objects. */
633
634static ui_file_write_ftype tee_file_write;
635static ui_file_fputs_ftype tee_file_fputs;
636static ui_file_isatty_ftype tee_file_isatty;
637static ui_file_delete_ftype tee_file_delete;
638static ui_file_flush_ftype tee_file_flush;
639
640static int tee_file_magic;
641
642struct tee_file
643 {
644 int *magic;
645 struct ui_file *one, *two;
646 int close_one, close_two;
647 };
648
649struct ui_file *
650tee_file_new (struct ui_file *one, int close_one,
651 struct ui_file *two, int close_two)
652{
653 struct ui_file *ui_file = ui_file_new ();
654 struct tee_file *tee = xmalloc (sizeof (struct tee_file));
5d502164 655
e4c242d9
DJ
656 tee->magic = &tee_file_magic;
657 tee->one = one;
658 tee->two = two;
659 tee->close_one = close_one;
660 tee->close_two = close_two;
661 set_ui_file_data (ui_file, tee, tee_file_delete);
662 set_ui_file_flush (ui_file, tee_file_flush);
663 set_ui_file_write (ui_file, tee_file_write);
664 set_ui_file_fputs (ui_file, tee_file_fputs);
665 set_ui_file_isatty (ui_file, tee_file_isatty);
666 return ui_file;
667}
668
669static void
670tee_file_delete (struct ui_file *file)
671{
672 struct tee_file *tee = ui_file_data (file);
5d502164 673
e4c242d9
DJ
674 if (tee->magic != &tee_file_magic)
675 internal_error (__FILE__, __LINE__,
e2e0b3e5 676 _("tee_file_delete: bad magic number"));
e4c242d9
DJ
677 if (tee->close_one)
678 ui_file_delete (tee->one);
679 if (tee->close_two)
680 ui_file_delete (tee->two);
681
682 xfree (tee);
683}
684
685static void
686tee_file_flush (struct ui_file *file)
687{
688 struct tee_file *tee = ui_file_data (file);
5d502164 689
e4c242d9
DJ
690 if (tee->magic != &tee_file_magic)
691 internal_error (__FILE__, __LINE__,
e2e0b3e5 692 _("tee_file_flush: bad magic number"));
e4c242d9
DJ
693 tee->one->to_flush (tee->one);
694 tee->two->to_flush (tee->two);
695}
696
697static void
698tee_file_write (struct ui_file *file, const char *buf, long length_buf)
699{
700 struct tee_file *tee = ui_file_data (file);
5d502164 701
e4c242d9
DJ
702 if (tee->magic != &tee_file_magic)
703 internal_error (__FILE__, __LINE__,
e2e0b3e5 704 _("tee_file_write: bad magic number"));
e4c242d9
DJ
705 ui_file_write (tee->one, buf, length_buf);
706 ui_file_write (tee->two, buf, length_buf);
707}
708
709static void
710tee_file_fputs (const char *linebuffer, struct ui_file *file)
711{
712 struct tee_file *tee = ui_file_data (file);
5d502164 713
e4c242d9
DJ
714 if (tee->magic != &tee_file_magic)
715 internal_error (__FILE__, __LINE__,
e2e0b3e5 716 _("tee_file_fputs: bad magic number"));
e4c242d9
DJ
717 tee->one->to_fputs (linebuffer, tee->one);
718 tee->two->to_fputs (linebuffer, tee->two);
719}
720
721static int
722tee_file_isatty (struct ui_file *file)
723{
724 struct tee_file *tee = ui_file_data (file);
5d502164 725
e4c242d9
DJ
726 if (tee->magic != &tee_file_magic)
727 internal_error (__FILE__, __LINE__,
e2e0b3e5 728 _("tee_file_isatty: bad magic number"));
172240dd
PA
729
730 return ui_file_isatty (tee->one);
e4c242d9 731}
This page took 1.116593 seconds and 4 git commands to generate.