Fix a lot of clang complaints
[platform/upstream/glib.git] / gio / goutputstream.c
1 /* GIO - GLib Input, Output and Streaming Library
2  * 
3  * Copyright (C) 2006-2007 Red Hat, Inc.
4  *
5  * This library is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU Lesser General Public
7  * License as published by the Free Software Foundation; either
8  * version 2 of the License, or (at your option) any later version.
9  *
10  * This library is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General
16  * Public License along with this library; if not, write to the
17  * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
18  * Boston, MA 02111-1307, USA.
19  *
20  * Author: Alexander Larsson <alexl@redhat.com>
21  */
22
23 #include "config.h"
24 #include "goutputstream.h"
25 #include "gcancellable.h"
26 #include "gasyncresult.h"
27 #include "gsimpleasyncresult.h"
28 #include "ginputstream.h"
29 #include "gioerror.h"
30 #include "glibintl.h"
31
32 #include "gioalias.h"
33
34 /**
35  * SECTION:goutputstream
36  * @short_description: Base class for implementing streaming output
37  * @include: gio/gio.h
38  *
39  * GOutputStream has functions to write to a stream (g_output_stream_write()),
40  * to close a stream (g_output_stream_close()) and to flush pending writes
41  * (g_output_stream_flush()). 
42  *
43  * To copy the content of an input stream to an output stream without 
44  * manually handling the reads and writes, use g_output_stream_splice(). 
45  *
46  * All of these functions have async variants too.
47  **/
48
49 G_DEFINE_TYPE (GOutputStream, g_output_stream, G_TYPE_OBJECT);
50
51 struct _GOutputStreamPrivate {
52   guint closed : 1;
53   guint pending : 1;
54   GAsyncReadyCallback outstanding_callback;
55 };
56
57 static gssize   g_output_stream_real_splice        (GOutputStream             *stream,
58                                                     GInputStream              *source,
59                                                     GOutputStreamSpliceFlags   flags,
60                                                     GCancellable              *cancellable,
61                                                     GError                   **error);
62 static void     g_output_stream_real_write_async   (GOutputStream             *stream,
63                                                     const void                *buffer,
64                                                     gsize                      count,
65                                                     int                        io_priority,
66                                                     GCancellable              *cancellable,
67                                                     GAsyncReadyCallback        callback,
68                                                     gpointer                   data);
69 static gssize   g_output_stream_real_write_finish  (GOutputStream             *stream,
70                                                     GAsyncResult              *result,
71                                                     GError                   **error);
72 static void     g_output_stream_real_splice_async  (GOutputStream             *stream,
73                                                     GInputStream              *source,
74                                                     GOutputStreamSpliceFlags   flags,
75                                                     int                        io_priority,
76                                                     GCancellable              *cancellable,
77                                                     GAsyncReadyCallback        callback,
78                                                     gpointer                   data);
79 static gssize   g_output_stream_real_splice_finish (GOutputStream             *stream,
80                                                     GAsyncResult              *result,
81                                                     GError                   **error);
82 static void     g_output_stream_real_flush_async   (GOutputStream             *stream,
83                                                     int                        io_priority,
84                                                     GCancellable              *cancellable,
85                                                     GAsyncReadyCallback        callback,
86                                                     gpointer                   data);
87 static gboolean g_output_stream_real_flush_finish  (GOutputStream             *stream,
88                                                     GAsyncResult              *result,
89                                                     GError                   **error);
90 static void     g_output_stream_real_close_async   (GOutputStream             *stream,
91                                                     int                        io_priority,
92                                                     GCancellable              *cancellable,
93                                                     GAsyncReadyCallback        callback,
94                                                     gpointer                   data);
95 static gboolean g_output_stream_real_close_finish  (GOutputStream             *stream,
96                                                     GAsyncResult              *result,
97                                                     GError                   **error);
98
99 static void
100 g_output_stream_finalize (GObject *object)
101 {
102   G_OBJECT_CLASS (g_output_stream_parent_class)->finalize (object);
103 }
104
105 static void
106 g_output_stream_dispose (GObject *object)
107 {
108   GOutputStream *stream;
109
110   stream = G_OUTPUT_STREAM (object);
111   
112   if (!stream->priv->closed)
113     g_output_stream_close (stream, NULL, NULL);
114
115   G_OBJECT_CLASS (g_output_stream_parent_class)->dispose (object);
116 }
117
118 static void
119 g_output_stream_class_init (GOutputStreamClass *klass)
120 {
121   GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
122   
123   g_type_class_add_private (klass, sizeof (GOutputStreamPrivate));
124   
125   gobject_class->finalize = g_output_stream_finalize;
126   gobject_class->dispose = g_output_stream_dispose;
127
128   klass->splice = g_output_stream_real_splice;
129   
130   klass->write_async = g_output_stream_real_write_async;
131   klass->write_finish = g_output_stream_real_write_finish;
132   klass->splice_async = g_output_stream_real_splice_async;
133   klass->splice_finish = g_output_stream_real_splice_finish;
134   klass->flush_async = g_output_stream_real_flush_async;
135   klass->flush_finish = g_output_stream_real_flush_finish;
136   klass->close_async = g_output_stream_real_close_async;
137   klass->close_finish = g_output_stream_real_close_finish;
138 }
139
140 static void
141 g_output_stream_init (GOutputStream *stream)
142 {
143   stream->priv = G_TYPE_INSTANCE_GET_PRIVATE (stream,
144                                               G_TYPE_OUTPUT_STREAM,
145                                               GOutputStreamPrivate);
146 }
147
148 /**
149  * g_output_stream_write:
150  * @stream: a #GOutputStream.
151  * @buffer: the buffer containing the data to write. 
152  * @count: the number of bytes to write
153  * @cancellable: optional cancellable object
154  * @error: location to store the error occuring, or %NULL to ignore
155  *
156  * Tries to write @count bytes from @buffer into the stream. Will block
157  * during the operation.
158  * 
159  * If count is zero returns zero and does nothing. A value of @count
160  * larger than %G_MAXSSIZE will cause a %G_IO_ERROR_INVALID_ARGUMENT error.
161  *
162  * On success, the number of bytes written to the stream is returned.
163  * It is not an error if this is not the same as the requested size, as it
164  * can happen e.g. on a partial i/o error, or if there is not enough
165  * storage in the stream. All writes either block until at least one byte
166  * is written, so zero is never returned (unless @count is zero).
167  * 
168  * If @cancellable is not NULL, then the operation can be cancelled by
169  * triggering the cancellable object from another thread. If the operation
170  * was cancelled, the error G_IO_ERROR_CANCELLED will be returned. If an
171  * operation was partially finished when the operation was cancelled the
172  * partial result will be returned, without an error.
173  *
174  * On error -1 is returned and @error is set accordingly.
175  * 
176  * Return value: Number of bytes written, or -1 on error
177  **/
178 gssize
179 g_output_stream_write (GOutputStream  *stream,
180                        const void     *buffer,
181                        gsize           count,
182                        GCancellable   *cancellable,
183                        GError        **error)
184 {
185   GOutputStreamClass *class;
186   gssize res;
187
188   g_return_val_if_fail (G_IS_OUTPUT_STREAM (stream), -1);
189   g_return_val_if_fail (buffer != NULL, 0);
190
191   if (count == 0)
192     return 0;
193   
194   if (((gssize) count) < 0)
195     {
196       g_set_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT,
197                    _("Too large count value passed to %s"), G_STRFUNC);
198       return -1;
199     }
200
201   class = G_OUTPUT_STREAM_GET_CLASS (stream);
202
203   if (class->write_fn == NULL) 
204     {
205       g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
206                            _("Output stream doesn't implement write"));
207       return -1;
208     }
209   
210   if (!g_output_stream_set_pending (stream, error))
211     return -1;
212   
213   if (cancellable)
214     g_cancellable_push_current (cancellable);
215   
216   res = class->write_fn (stream, buffer, count, cancellable, error);
217   
218   if (cancellable)
219     g_cancellable_pop_current (cancellable);
220   
221   g_output_stream_clear_pending (stream);
222
223   return res; 
224 }
225
226 /**
227  * g_output_stream_write_all:
228  * @stream: a #GOutputStream.
229  * @buffer: the buffer containing the data to write. 
230  * @count: the number of bytes to write
231  * @bytes_written: location to store the number of bytes that was 
232  *     written to the stream
233  * @cancellable: optional #GCancellable object, %NULL to ignore.
234  * @error: location to store the error occuring, or %NULL to ignore
235  *
236  * Tries to write @count bytes from @buffer into the stream. Will block
237  * during the operation.
238  * 
239  * This function is similar to g_output_stream_write(), except it tries to
240  * write as many bytes as requested, only stopping on an error.
241  *
242  * On a successful write of @count bytes, %TRUE is returned, and @bytes_written
243  * is set to @count.
244  * 
245  * If there is an error during the operation FALSE is returned and @error
246  * is set to indicate the error status, @bytes_written is updated to contain
247  * the number of bytes written into the stream before the error occurred.
248  *
249  * Return value: %TRUE on success, %FALSE if there was an error
250  **/
251 gboolean
252 g_output_stream_write_all (GOutputStream  *stream,
253                            const void     *buffer,
254                            gsize           count,
255                            gsize          *bytes_written,
256                            GCancellable   *cancellable,
257                            GError        **error)
258 {
259   gsize _bytes_written;
260   gssize res;
261
262   g_return_val_if_fail (G_IS_OUTPUT_STREAM (stream), FALSE);
263   g_return_val_if_fail (buffer != NULL, FALSE);
264
265   _bytes_written = 0;
266   while (_bytes_written < count)
267     {
268       res = g_output_stream_write (stream, (char *)buffer + _bytes_written, count - _bytes_written,
269                                    cancellable, error);
270       if (res == -1)
271         {
272           if (bytes_written)
273             *bytes_written = _bytes_written;
274           return FALSE;
275         }
276       
277       if (res == 0)
278         g_warning ("Write returned zero without error");
279
280       _bytes_written += res;
281     }
282   
283   if (bytes_written)
284     *bytes_written = _bytes_written;
285
286   return TRUE;
287 }
288
289 /**
290  * g_output_stream_flush:
291  * @stream: a #GOutputStream.
292  * @cancellable: optional cancellable object
293  * @error: location to store the error occuring, or %NULL to ignore
294  *
295  * Flushed any outstanding buffers in the stream. Will block during 
296  * the operation. Closing the stream will implicitly cause a flush.
297  *
298  * This function is optional for inherited classes.
299  * 
300  * If @cancellable is not %NULL, then the operation can be cancelled by
301  * triggering the cancellable object from another thread. If the operation
302  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
303  *
304  * Return value: %TRUE on success, %FALSE on error
305  **/
306 gboolean
307 g_output_stream_flush (GOutputStream  *stream,
308                        GCancellable   *cancellable,
309                        GError        **error)
310 {
311   GOutputStreamClass *class;
312   gboolean res;
313
314   g_return_val_if_fail (G_IS_OUTPUT_STREAM (stream), FALSE);
315
316   if (!g_output_stream_set_pending (stream, error))
317     return FALSE;
318   
319   class = G_OUTPUT_STREAM_GET_CLASS (stream);
320
321   res = TRUE;
322   if (class->flush)
323     {
324       if (cancellable)
325         g_cancellable_push_current (cancellable);
326       
327       res = class->flush (stream, cancellable, error);
328       
329       if (cancellable)
330         g_cancellable_pop_current (cancellable);
331     }
332   
333   g_output_stream_clear_pending (stream);
334
335   return res;
336 }
337
338 /**
339  * g_output_stream_splice:
340  * @stream: a #GOutputStream.
341  * @source: a #GInputStream.
342  * @flags: a set of #GOutputStreamSpliceFlags.
343  * @cancellable: optional #GCancellable object, %NULL to ignore.
344  * @error: a #GError location to store the error occuring, or %NULL to
345  * ignore.
346  *
347  * Splices an input stream into an output stream.
348  *
349  * Returns: a #gssize containing the size of the data spliced, or
350  *     -1 if an error occurred.
351  **/
352 gssize
353 g_output_stream_splice (GOutputStream             *stream,
354                         GInputStream              *source,
355                         GOutputStreamSpliceFlags   flags,
356                         GCancellable              *cancellable,
357                         GError                   **error)
358 {
359   GOutputStreamClass *class;
360   gssize bytes_copied;
361
362   g_return_val_if_fail (G_IS_OUTPUT_STREAM (stream), -1);
363   g_return_val_if_fail (G_IS_INPUT_STREAM (source), -1);
364
365   if (g_input_stream_is_closed (source))
366     {
367       g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_CLOSED,
368                            _("Source stream is already closed"));
369       return -1;
370     }
371
372   if (!g_output_stream_set_pending (stream, error))
373     return -1;
374
375   class = G_OUTPUT_STREAM_GET_CLASS (stream);
376
377   if (cancellable)
378     g_cancellable_push_current (cancellable);
379
380   bytes_copied = class->splice (stream, source, flags, cancellable, error);
381
382   if (cancellable)
383     g_cancellable_pop_current (cancellable);
384
385   g_output_stream_clear_pending (stream);
386
387   return bytes_copied;
388 }
389
390 static gssize
391 g_output_stream_real_splice (GOutputStream             *stream,
392                              GInputStream              *source,
393                              GOutputStreamSpliceFlags   flags,
394                              GCancellable              *cancellable,
395                              GError                   **error)
396 {
397   GOutputStreamClass *class = G_OUTPUT_STREAM_GET_CLASS (stream);
398   gssize n_read, n_written;
399   gssize bytes_copied;
400   char buffer[8192], *p;
401   gboolean res;
402
403   bytes_copied = 0;
404   if (class->write_fn == NULL)
405     {
406       g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
407                            _("Output stream doesn't implement write"));
408       res = FALSE;
409       goto notsupported;
410     }
411
412   res = TRUE;
413   do
414     {
415       n_read = g_input_stream_read (source, buffer, sizeof (buffer), cancellable, error);
416       if (n_read == -1)
417         {
418           res = FALSE;
419           break;
420         }
421
422       if (n_read == 0)
423         break;
424
425       p = buffer;
426       while (n_read > 0)
427         {
428           n_written = class->write_fn (stream, p, n_read, cancellable, error);
429           if (n_written == -1)
430             {
431               res = FALSE;
432               break;
433             }
434
435           p += n_written;
436           n_read -= n_written;
437           bytes_copied += n_written;
438         }
439     }
440   while (res);
441
442  notsupported:
443   if (!res)
444     error = NULL; /* Ignore further errors */
445
446   if (flags & G_OUTPUT_STREAM_SPLICE_CLOSE_SOURCE)
447     {
448       /* Don't care about errors in source here */
449       g_input_stream_close (source, cancellable, NULL);
450     }
451
452   if (flags & G_OUTPUT_STREAM_SPLICE_CLOSE_TARGET)
453     {
454       /* But write errors on close are bad! */
455       if (class->close_fn &&
456           !class->close_fn (stream, cancellable, error))
457         res = FALSE;
458     }
459
460   if (res)
461     return bytes_copied;
462
463   return -1;
464 }
465
466
467 /**
468  * g_output_stream_close:
469  * @stream: A #GOutputStream.
470  * @cancellable: optional cancellable object
471  * @error: location to store the error occuring, or %NULL to ignore
472  *
473  * Closes the stream, releasing resources related to it.
474  *
475  * Once the stream is closed, all other operations will return %G_IO_ERROR_CLOSED.
476  * Closing a stream multiple times will not return an error.
477  *
478  * Closing a stream will automatically flush any outstanding buffers in the
479  * stream.
480  *
481  * Streams will be automatically closed when the last reference
482  * is dropped, but you might want to call this function to make sure 
483  * resources are released as early as possible.
484  *
485  * Some streams might keep the backing store of the stream (e.g. a file descriptor)
486  * open after the stream is closed. See the documentation for the individual
487  * stream for details.
488  *
489  * On failure the first error that happened will be reported, but the close
490  * operation will finish as much as possible. A stream that failed to
491  * close will still return %G_IO_ERROR_CLOSED for all operations. Still, it
492  * is important to check and report the error to the user, otherwise
493  * there might be a loss of data as all data might not be written.
494  * 
495  * If @cancellable is not NULL, then the operation can be cancelled by
496  * triggering the cancellable object from another thread. If the operation
497  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
498  * Cancelling a close will still leave the stream closed, but there some streams
499  * can use a faster close that doesn't block to e.g. check errors. On
500  * cancellation (as with any error) there is no guarantee that all written
501  * data will reach the target. 
502  *
503  * Return value: %TRUE on success, %FALSE on failure
504  **/
505 gboolean
506 g_output_stream_close (GOutputStream  *stream,
507                        GCancellable   *cancellable,
508                        GError        **error)
509 {
510   GOutputStreamClass *class;
511   gboolean res;
512
513   g_return_val_if_fail (G_IS_OUTPUT_STREAM (stream), FALSE);
514
515   class = G_OUTPUT_STREAM_GET_CLASS (stream);
516
517   if (stream->priv->closed)
518     return TRUE;
519
520   if (!g_output_stream_set_pending (stream, error))
521     return FALSE;
522
523   if (cancellable)
524     g_cancellable_push_current (cancellable);
525
526   if (class->flush)
527     res = class->flush (stream, cancellable, error);
528   else
529     res = TRUE;
530   
531   if (!res)
532     {
533       /* flushing caused the error that we want to return,
534        * but we still want to close the underlying stream if possible
535        */
536       if (class->close_fn)
537         class->close_fn (stream, cancellable, NULL);
538     }
539   else
540     {
541       res = TRUE;
542       if (class->close_fn)
543         res = class->close_fn (stream, cancellable, error);
544     }
545   
546   if (cancellable)
547     g_cancellable_pop_current (cancellable);
548   
549   stream->priv->closed = TRUE;
550   g_output_stream_clear_pending (stream);
551   
552   return res;
553 }
554
555 static void
556 async_ready_callback_wrapper (GObject      *source_object,
557                               GAsyncResult *res,
558                               gpointer      user_data)
559 {
560   GOutputStream *stream = G_OUTPUT_STREAM (source_object);
561
562   g_output_stream_clear_pending (stream);
563   if (stream->priv->outstanding_callback)
564     (*stream->priv->outstanding_callback) (source_object, res, user_data);
565   g_object_unref (stream);
566 }
567
568 static void
569 async_ready_close_callback_wrapper (GObject      *source_object,
570                                     GAsyncResult *res,
571                                     gpointer      user_data)
572 {
573   GOutputStream *stream = G_OUTPUT_STREAM (source_object);
574
575   stream->priv->closed = TRUE;
576   g_output_stream_clear_pending (stream);
577   if (stream->priv->outstanding_callback)
578     (*stream->priv->outstanding_callback) (source_object, res, user_data);
579   g_object_unref (stream);
580 }
581
582 /**
583  * g_output_stream_write_async:
584  * @stream: A #GOutputStream.
585  * @buffer: the buffer containing the data to write. 
586  * @count: the number of bytes to write
587  * @io_priority: the io priority of the request.
588  * @cancellable: optional #GCancellable object, %NULL to ignore.
589  * @callback: callback to call when the request is satisfied
590  * @user_data: the data to pass to callback function
591  *
592  * Request an asynchronous write of @count bytes from @buffer into 
593  * the stream. When the operation is finished @callback will be called.
594  * You can then call g_output_stream_write_finish() to get the result of the 
595  * operation.
596  *
597  * During an async request no other sync and async calls are allowed, 
598  * and will result in %G_IO_ERROR_PENDING errors. 
599  *
600  * A value of @count larger than %G_MAXSSIZE will cause a 
601  * %G_IO_ERROR_INVALID_ARGUMENT error.
602  *
603  * On success, the number of bytes written will be passed to the
604  * @callback. It is not an error if this is not the same as the 
605  * requested size, as it can happen e.g. on a partial I/O error, 
606  * but generally we try to write as many bytes as requested. 
607  *
608  * Any outstanding I/O request with higher priority (lower numerical 
609  * value) will be executed before an outstanding request with lower 
610  * priority. Default priority is %G_PRIORITY_DEFAULT.
611  *
612  * The asyncronous methods have a default fallback that uses threads 
613  * to implement asynchronicity, so they are optional for inheriting 
614  * classes. However, if you override one you must override all.
615  *
616  * For the synchronous, blocking version of this function, see 
617  * g_output_stream_write().
618  **/
619 void
620 g_output_stream_write_async (GOutputStream       *stream,
621                              const void          *buffer,
622                              gsize                count,
623                              int                  io_priority,
624                              GCancellable        *cancellable,
625                              GAsyncReadyCallback  callback,
626                              gpointer             user_data)
627 {
628   GOutputStreamClass *class;
629   GSimpleAsyncResult *simple;
630   GError *error = NULL;
631
632   g_return_if_fail (G_IS_OUTPUT_STREAM (stream));
633   g_return_if_fail (buffer != NULL);
634
635   if (count == 0)
636     {
637       simple = g_simple_async_result_new (G_OBJECT (stream),
638                                           callback,
639                                           user_data,
640                                           g_output_stream_write_async);
641       g_simple_async_result_complete_in_idle (simple);
642       g_object_unref (simple);
643       return;
644     }
645
646   if (((gssize) count) < 0)
647     {
648       g_simple_async_report_error_in_idle (G_OBJECT (stream),
649                                            callback,
650                                            user_data,
651                                            G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT,
652                                            _("Too large count value passed to %s"),
653                                            G_STRFUNC);
654       return;
655     }
656
657   if (!g_output_stream_set_pending (stream, &error))
658     {
659       g_simple_async_report_gerror_in_idle (G_OBJECT (stream),
660                                             callback,
661                                             user_data,
662                                             error);
663       g_error_free (error);
664       return;
665     }
666   
667   class = G_OUTPUT_STREAM_GET_CLASS (stream);
668
669   stream->priv->outstanding_callback = callback;
670   g_object_ref (stream);
671   class->write_async (stream, buffer, count, io_priority, cancellable,
672                       async_ready_callback_wrapper, user_data);
673 }
674
675 /**
676  * g_output_stream_write_finish:
677  * @stream: a #GOutputStream.
678  * @result: a #GAsyncResult.
679  * @error: a #GError location to store the error occuring, or %NULL to 
680  * ignore.
681  * 
682  * Finishes a stream write operation.
683  * 
684  * Returns: a #gssize containing the number of bytes written to the stream.
685  **/
686 gssize
687 g_output_stream_write_finish (GOutputStream  *stream,
688                               GAsyncResult   *result,
689                               GError        **error)
690 {
691   GSimpleAsyncResult *simple;
692   GOutputStreamClass *class;
693
694   g_return_val_if_fail (G_IS_OUTPUT_STREAM (stream), -1);
695   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), -1);
696
697   if (G_IS_SIMPLE_ASYNC_RESULT (result))
698     {
699       simple = G_SIMPLE_ASYNC_RESULT (result);
700       if (g_simple_async_result_propagate_error (simple, error))
701         return -1;
702
703       /* Special case writes of 0 bytes */
704       if (g_simple_async_result_get_source_tag (simple) == g_output_stream_write_async)
705         return 0;
706     }
707   
708   class = G_OUTPUT_STREAM_GET_CLASS (stream);
709   return class->write_finish (stream, result, error);
710 }
711
712 typedef struct {
713   GInputStream *source;
714   gpointer user_data;
715   GAsyncReadyCallback callback;
716 } SpliceUserData;
717
718 static void
719 async_ready_splice_callback_wrapper (GObject      *source_object,
720                                      GAsyncResult *res,
721                                      gpointer     _data)
722 {
723   GOutputStream *stream = G_OUTPUT_STREAM (source_object);
724   SpliceUserData *data = _data;
725   
726   g_output_stream_clear_pending (stream);
727   
728   if (data->callback)
729     (*data->callback) (source_object, res, data->user_data);
730   
731   g_object_unref (stream);
732   g_object_unref (data->source);
733   g_free (data);
734 }
735
736 /**
737  * g_output_stream_splice_async:
738  * @stream: a #GOutputStream.
739  * @source: a #GInputStream. 
740  * @flags: a set of #GOutputStreamSpliceFlags.
741  * @io_priority: the io priority of the request.
742  * @cancellable: optional #GCancellable object, %NULL to ignore. 
743  * @callback: a #GAsyncReadyCallback. 
744  * @user_data: user data passed to @callback.
745  * 
746  * Splices a stream asynchronously.
747  * When the operation is finished @callback will be called.
748  * You can then call g_output_stream_splice_finish() to get the 
749  * result of the operation.
750  *
751  * For the synchronous, blocking version of this function, see 
752  * g_output_stream_splice().
753  **/
754 void
755 g_output_stream_splice_async (GOutputStream            *stream,
756                               GInputStream             *source,
757                               GOutputStreamSpliceFlags  flags,
758                               int                       io_priority,
759                               GCancellable             *cancellable,
760                               GAsyncReadyCallback       callback,
761                               gpointer                  user_data)
762 {
763   GOutputStreamClass *class;
764   SpliceUserData *data;
765   GError *error = NULL;
766
767   g_return_if_fail (G_IS_OUTPUT_STREAM (stream));
768   g_return_if_fail (G_IS_INPUT_STREAM (source));
769
770   if (g_input_stream_is_closed (source))
771     {
772       g_simple_async_report_error_in_idle (G_OBJECT (stream),
773                                            callback,
774                                            user_data,
775                                            G_IO_ERROR, G_IO_ERROR_CLOSED,
776                                            _("Source stream is already closed"));
777       return;
778     }
779   
780   if (!g_output_stream_set_pending (stream, &error))
781     {
782       g_simple_async_report_gerror_in_idle (G_OBJECT (stream),
783                                             callback,
784                                             user_data,
785                                             error);
786       g_error_free (error);
787       return;
788     }
789
790   class = G_OUTPUT_STREAM_GET_CLASS (stream);
791
792   data = g_new0 (SpliceUserData, 1);
793   data->callback = callback;
794   data->user_data = user_data;
795   data->source = g_object_ref (source);
796   
797   g_object_ref (stream);
798   class->splice_async (stream, source, flags, io_priority, cancellable,
799                       async_ready_splice_callback_wrapper, data);
800 }
801
802 /**
803  * g_output_stream_splice_finish:
804  * @stream: a #GOutputStream.
805  * @result: a #GAsyncResult.
806  * @error: a #GError location to store the error occuring, or %NULL to 
807  * ignore.
808  *
809  * Finishes an asynchronous stream splice operation.
810  * 
811  * Returns: a #gssize of the number of bytes spliced.
812  **/
813 gssize
814 g_output_stream_splice_finish (GOutputStream  *stream,
815                                GAsyncResult   *result,
816                                GError        **error)
817 {
818   GSimpleAsyncResult *simple;
819   GOutputStreamClass *class;
820
821   g_return_val_if_fail (G_IS_OUTPUT_STREAM (stream), -1);
822   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), -1);
823
824   if (G_IS_SIMPLE_ASYNC_RESULT (result))
825     {
826       simple = G_SIMPLE_ASYNC_RESULT (result);
827       if (g_simple_async_result_propagate_error (simple, error))
828         return -1;
829     }
830   
831   class = G_OUTPUT_STREAM_GET_CLASS (stream);
832   return class->splice_finish (stream, result, error);
833 }
834
835 /**
836  * g_output_stream_flush_async:
837  * @stream: a #GOutputStream.
838  * @io_priority: the io priority of the request.
839  * @cancellable: optional #GCancellable object, %NULL to ignore.
840  * @callback: a #GAsyncReadyCallback to call when the request is satisfied
841  * @user_data: the data to pass to callback function
842  * 
843  * Flushes a stream asynchronously.
844  * For behaviour details see g_output_stream_flush().
845  *
846  * When the operation is finished @callback will be 
847  * called. You can then call g_output_stream_flush_finish() to get the 
848  * result of the operation.
849  **/
850 void
851 g_output_stream_flush_async (GOutputStream       *stream,
852                              int                  io_priority,
853                              GCancellable        *cancellable,
854                              GAsyncReadyCallback  callback,
855                              gpointer             user_data)
856 {
857   GOutputStreamClass *class;
858   GSimpleAsyncResult *simple;
859   GError *error = NULL;
860
861   g_return_if_fail (G_IS_OUTPUT_STREAM (stream));
862
863   if (!g_output_stream_set_pending (stream, &error))
864     {
865       g_simple_async_report_gerror_in_idle (G_OBJECT (stream),
866                                             callback,
867                                             user_data,
868                                             error);
869       g_error_free (error);
870       return;
871     }
872
873   stream->priv->outstanding_callback = callback;
874   g_object_ref (stream);
875
876   class = G_OUTPUT_STREAM_GET_CLASS (stream);
877   
878   if (class->flush_async == NULL)
879     {
880       simple = g_simple_async_result_new (G_OBJECT (stream),
881                                           async_ready_callback_wrapper,
882                                           user_data,
883                                           g_output_stream_flush_async);
884       g_simple_async_result_complete_in_idle (simple);
885       g_object_unref (simple);
886       return;
887     }
888       
889   class->flush_async (stream, io_priority, cancellable,
890                       async_ready_callback_wrapper, user_data);
891 }
892
893 /**
894  * g_output_stream_flush_finish:
895  * @stream: a #GOutputStream.
896  * @result: a GAsyncResult.
897  * @error: a #GError location to store the error occuring, or %NULL to 
898  * ignore.
899  * 
900  * Finishes flushing an output stream.
901  * 
902  * Returns: %TRUE if flush operation suceeded, %FALSE otherwise.
903  **/
904 gboolean
905 g_output_stream_flush_finish (GOutputStream  *stream,
906                               GAsyncResult   *result,
907                               GError        **error)
908 {
909   GSimpleAsyncResult *simple;
910   GOutputStreamClass *klass;
911
912   g_return_val_if_fail (G_IS_OUTPUT_STREAM (stream), FALSE);
913   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), FALSE);
914
915   if (G_IS_SIMPLE_ASYNC_RESULT (result))
916     {
917       simple = G_SIMPLE_ASYNC_RESULT (result);
918       if (g_simple_async_result_propagate_error (simple, error))
919         return FALSE;
920
921       /* Special case default implementation */
922       if (g_simple_async_result_get_source_tag (simple) == g_output_stream_flush_async)
923         return TRUE;
924     }
925
926   klass = G_OUTPUT_STREAM_GET_CLASS (stream);
927   return klass->flush_finish (stream, result, error);
928 }
929
930
931 /**
932  * g_output_stream_close_async:
933  * @stream: A #GOutputStream.
934  * @io_priority: the io priority of the request.
935  * @callback: callback to call when the request is satisfied
936  * @user_data: the data to pass to callback function
937  * @cancellable: optional cancellable object
938  *
939  * Requests an asynchronous close of the stream, releasing resources 
940  * related to it. When the operation is finished @callback will be 
941  * called. You can then call g_output_stream_close_finish() to get 
942  * the result of the operation.
943  *
944  * For behaviour details see g_output_stream_close().
945  *
946  * The asyncronous methods have a default fallback that uses threads 
947  * to implement asynchronicity, so they are optional for inheriting 
948  * classes. However, if you override one you must override all.
949  **/
950 void
951 g_output_stream_close_async (GOutputStream       *stream,
952                              int                  io_priority,
953                              GCancellable        *cancellable,
954                              GAsyncReadyCallback  callback,
955                              gpointer             user_data)
956 {
957   GOutputStreamClass *class;
958   GSimpleAsyncResult *simple;
959   GError *error = NULL;
960
961   g_return_if_fail (G_IS_OUTPUT_STREAM (stream));
962   
963   if (stream->priv->closed)
964     {
965       simple = g_simple_async_result_new (G_OBJECT (stream),
966                                           callback,
967                                           user_data,
968                                           g_output_stream_close_async);
969       g_simple_async_result_complete_in_idle (simple);
970       g_object_unref (simple);
971       return;
972     }
973
974   if (!g_output_stream_set_pending (stream, &error))
975     {
976       g_simple_async_report_gerror_in_idle (G_OBJECT (stream),
977                                             callback,
978                                             user_data,
979                                             error);
980       g_error_free (error);
981       return;
982     }
983   
984   class = G_OUTPUT_STREAM_GET_CLASS (stream);
985   stream->priv->outstanding_callback = callback;
986   g_object_ref (stream);
987   class->close_async (stream, io_priority, cancellable,
988                       async_ready_close_callback_wrapper, user_data);
989 }
990
991 /**
992  * g_output_stream_close_finish:
993  * @stream: a #GOutputStream.
994  * @result: a #GAsyncResult.
995  * @error: a #GError location to store the error occuring, or %NULL to 
996  * ignore.
997  * 
998  * Closes an output stream.
999  * 
1000  * Returns: %TRUE if stream was successfully closed, %FALSE otherwise.
1001  **/
1002 gboolean
1003 g_output_stream_close_finish (GOutputStream  *stream,
1004                               GAsyncResult   *result,
1005                               GError        **error)
1006 {
1007   GSimpleAsyncResult *simple;
1008   GOutputStreamClass *class;
1009
1010   g_return_val_if_fail (G_IS_OUTPUT_STREAM (stream), FALSE);
1011   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), FALSE);
1012
1013   if (G_IS_SIMPLE_ASYNC_RESULT (result))
1014     {
1015       simple = G_SIMPLE_ASYNC_RESULT (result);
1016       if (g_simple_async_result_propagate_error (simple, error))
1017         return FALSE;
1018
1019       /* Special case already closed */
1020       if (g_simple_async_result_get_source_tag (simple) == g_output_stream_close_async)
1021         return TRUE;
1022     }
1023
1024   class = G_OUTPUT_STREAM_GET_CLASS (stream);
1025   return class->close_finish (stream, result, error);
1026 }
1027
1028 /**
1029  * g_output_stream_is_closed:
1030  * @stream: a #GOutputStream.
1031  * 
1032  * Checks if an output stream has already been closed.
1033  * 
1034  * Returns: %TRUE if @stream is closed. %FALSE otherwise. 
1035  **/
1036 gboolean
1037 g_output_stream_is_closed (GOutputStream *stream)
1038 {
1039   g_return_val_if_fail (G_IS_OUTPUT_STREAM (stream), TRUE);
1040   
1041   return stream->priv->closed;
1042 }
1043
1044 /**
1045  * g_output_stream_has_pending:
1046  * @stream: a #GOutputStream.
1047  * 
1048  * Checks if an ouput stream has pending actions.
1049  * 
1050  * Returns: %TRUE if @stream has pending actions. 
1051  **/
1052 gboolean
1053 g_output_stream_has_pending (GOutputStream *stream)
1054 {
1055   g_return_val_if_fail (G_IS_OUTPUT_STREAM (stream), FALSE);
1056   
1057   return stream->priv->pending;
1058 }
1059
1060 /**
1061  * g_output_stream_set_pending:
1062  * @stream: a #GOutputStream.
1063  * @error: a #GError location to store the error occuring, or %NULL to 
1064  * ignore.
1065  * 
1066  * Sets @stream to have actions pending. If the pending flag is
1067  * already set or @stream is closed, it will return %FALSE and set
1068  * @error.
1069  *
1070  * Return value: %TRUE if pending was previously unset and is now set.
1071  **/
1072 gboolean
1073 g_output_stream_set_pending (GOutputStream *stream,
1074                              GError **error)
1075 {
1076   g_return_val_if_fail (G_IS_OUTPUT_STREAM (stream), FALSE);
1077   
1078   if (stream->priv->closed)
1079     {
1080       g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_CLOSED,
1081                            _("Stream is already closed"));
1082       return FALSE;
1083     }
1084   
1085   if (stream->priv->pending)
1086     {
1087       g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_PENDING,
1088                            /* Translators: This is an error you get if there is
1089                             * already an operation running against this stream when
1090                             * you try to start one */
1091                            _("Stream has outstanding operation"));
1092       return FALSE;
1093     }
1094   
1095   stream->priv->pending = TRUE;
1096   return TRUE;
1097 }
1098
1099 /**
1100  * g_output_stream_clear_pending:
1101  * @stream: output stream
1102  * 
1103  * Clears the pending flag on @stream.
1104  **/
1105 void
1106 g_output_stream_clear_pending (GOutputStream *stream)
1107 {
1108   g_return_if_fail (G_IS_OUTPUT_STREAM (stream));
1109   
1110   stream->priv->pending = FALSE;
1111 }
1112
1113
1114 /********************************************
1115  *   Default implementation of async ops    *
1116  ********************************************/
1117
1118 typedef struct {
1119   const void         *buffer;
1120   gsize               count_requested;
1121   gssize              count_written;
1122 } WriteData;
1123
1124 static void
1125 write_async_thread (GSimpleAsyncResult *res,
1126                     GObject            *object,
1127                     GCancellable       *cancellable)
1128 {
1129   WriteData *op;
1130   GOutputStreamClass *class;
1131   GError *error = NULL;
1132
1133   class = G_OUTPUT_STREAM_GET_CLASS (object);
1134   op = g_simple_async_result_get_op_res_gpointer (res);
1135   op->count_written = class->write_fn (G_OUTPUT_STREAM (object), op->buffer, op->count_requested,
1136                                        cancellable, &error);
1137   if (op->count_written == -1)
1138     {
1139       g_simple_async_result_set_from_error (res, error);
1140       g_error_free (error);
1141     }
1142 }
1143
1144 static void
1145 g_output_stream_real_write_async (GOutputStream       *stream,
1146                                   const void          *buffer,
1147                                   gsize                count,
1148                                   int                  io_priority,
1149                                   GCancellable        *cancellable,
1150                                   GAsyncReadyCallback  callback,
1151                                   gpointer             user_data)
1152 {
1153   GSimpleAsyncResult *res;
1154   WriteData *op;
1155
1156   op = g_new0 (WriteData, 1);
1157   res = g_simple_async_result_new (G_OBJECT (stream), callback, user_data, g_output_stream_real_write_async);
1158   g_simple_async_result_set_op_res_gpointer (res, op, g_free);
1159   op->buffer = buffer;
1160   op->count_requested = count;
1161   
1162   g_simple_async_result_run_in_thread (res, write_async_thread, io_priority, cancellable);
1163   g_object_unref (res);
1164 }
1165
1166 static gssize
1167 g_output_stream_real_write_finish (GOutputStream  *stream,
1168                                    GAsyncResult   *result,
1169                                    GError        **error)
1170 {
1171   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
1172   WriteData *op;
1173
1174   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_output_stream_real_write_async);
1175   op = g_simple_async_result_get_op_res_gpointer (simple);
1176   return op->count_written;
1177 }
1178
1179 typedef struct {
1180   GInputStream *source;
1181   GOutputStreamSpliceFlags flags;
1182   gssize bytes_copied;
1183 } SpliceData;
1184
1185 static void
1186 splice_async_thread (GSimpleAsyncResult *result,
1187                      GObject            *object,
1188                      GCancellable       *cancellable)
1189 {
1190   SpliceData *op;
1191   GOutputStreamClass *class;
1192   GError *error = NULL;
1193   GOutputStream *stream;
1194
1195   stream = G_OUTPUT_STREAM (object);
1196   class = G_OUTPUT_STREAM_GET_CLASS (object);
1197   op = g_simple_async_result_get_op_res_gpointer (result);
1198   
1199   op->bytes_copied = class->splice (stream,
1200                                     op->source,
1201                                     op->flags,
1202                                     cancellable,
1203                                     &error);
1204   if (op->bytes_copied == -1)
1205     {
1206       g_simple_async_result_set_from_error (result, error);
1207       g_error_free (error);
1208     }
1209 }
1210
1211 static void
1212 g_output_stream_real_splice_async (GOutputStream             *stream,
1213                                    GInputStream              *source,
1214                                    GOutputStreamSpliceFlags   flags,
1215                                    int                        io_priority,
1216                                    GCancellable              *cancellable,
1217                                    GAsyncReadyCallback        callback,
1218                                    gpointer                   user_data)
1219 {
1220   GSimpleAsyncResult *res;
1221   SpliceData *op;
1222
1223   op = g_new0 (SpliceData, 1);
1224   res = g_simple_async_result_new (G_OBJECT (stream), callback, user_data, g_output_stream_real_splice_async);
1225   g_simple_async_result_set_op_res_gpointer (res, op, g_free);
1226   op->flags = flags;
1227   op->source = source;
1228
1229   /* TODO: In the case where both source and destintion have
1230      non-threadbased async calls we can use a true async copy here */
1231   
1232   g_simple_async_result_run_in_thread (res, splice_async_thread, io_priority, cancellable);
1233   g_object_unref (res);
1234 }
1235
1236 static gssize
1237 g_output_stream_real_splice_finish (GOutputStream  *stream,
1238                                     GAsyncResult   *result,
1239                                     GError        **error)
1240 {
1241   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
1242   SpliceData *op;
1243
1244   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_output_stream_real_splice_async);
1245   op = g_simple_async_result_get_op_res_gpointer (simple);
1246   return op->bytes_copied;
1247 }
1248
1249
1250 static void
1251 flush_async_thread (GSimpleAsyncResult *res,
1252                     GObject            *object,
1253                     GCancellable       *cancellable)
1254 {
1255   GOutputStreamClass *class;
1256   gboolean result;
1257   GError *error = NULL;
1258
1259   class = G_OUTPUT_STREAM_GET_CLASS (object);
1260   result = TRUE;
1261   if (class->flush)
1262     result = class->flush (G_OUTPUT_STREAM (object), cancellable, &error);
1263
1264   if (!result)
1265     {
1266       g_simple_async_result_set_from_error (res, error);
1267       g_error_free (error);
1268     }
1269 }
1270
1271 static void
1272 g_output_stream_real_flush_async (GOutputStream       *stream,
1273                                   int                  io_priority,
1274                                   GCancellable        *cancellable,
1275                                   GAsyncReadyCallback  callback,
1276                                   gpointer             user_data)
1277 {
1278   GSimpleAsyncResult *res;
1279
1280   res = g_simple_async_result_new (G_OBJECT (stream), callback, user_data, g_output_stream_real_write_async);
1281   
1282   g_simple_async_result_run_in_thread (res, flush_async_thread, io_priority, cancellable);
1283   g_object_unref (res);
1284 }
1285
1286 static gboolean
1287 g_output_stream_real_flush_finish (GOutputStream  *stream,
1288                                    GAsyncResult   *result,
1289                                    GError        **error)
1290 {
1291   return TRUE;
1292 }
1293
1294 static void
1295 close_async_thread (GSimpleAsyncResult *res,
1296                     GObject            *object,
1297                     GCancellable       *cancellable)
1298 {
1299   GOutputStreamClass *class;
1300   GError *error = NULL;
1301   gboolean result;
1302
1303   /* Auto handling of cancelation disabled, and ignore
1304      cancellation, since we want to close things anyway, although
1305      possibly in a quick-n-dirty way. At least we never want to leak
1306      open handles */
1307
1308   class = G_OUTPUT_STREAM_GET_CLASS (object);
1309   if (class->close_fn)
1310     {
1311       result = class->close_fn (G_OUTPUT_STREAM (object), cancellable, &error);
1312       if (!result)
1313         {
1314           g_simple_async_result_set_from_error (res, error);
1315           g_error_free (error);
1316         }
1317     }
1318 }
1319
1320 static void
1321 g_output_stream_real_close_async (GOutputStream       *stream,
1322                                   int                  io_priority,
1323                                   GCancellable        *cancellable,
1324                                   GAsyncReadyCallback  callback,
1325                                   gpointer             user_data)
1326 {
1327   GSimpleAsyncResult *res;
1328   
1329   res = g_simple_async_result_new (G_OBJECT (stream), callback, user_data, g_output_stream_real_close_async);
1330
1331   g_simple_async_result_set_handle_cancellation (res, FALSE);
1332   
1333   g_simple_async_result_run_in_thread (res, close_async_thread, io_priority, cancellable);
1334   g_object_unref (res);
1335 }
1336
1337 static gboolean
1338 g_output_stream_real_close_finish (GOutputStream  *stream,
1339                                    GAsyncResult   *result,
1340                                    GError        **error)
1341 {
1342   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
1343   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_output_stream_real_close_async);
1344   return TRUE;
1345 }
1346
1347 #define __G_OUTPUT_STREAM_C__
1348 #include "gioaliasdef.c"