gfile: Don't use C++ keyword "template" as variable name
[platform/upstream/glib.git] / gio / gfile.c
1 /* -*- mode: C; c-file-style: "gnu"; indent-tabs-mode: nil; -*- */
2
3 /* GIO - GLib Input, Output and Streaming Library
4  * 
5  * Copyright (C) 2006-2007 Red Hat, Inc.
6  *
7  * This library is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Lesser General Public
9  * License as published by the Free Software Foundation; either
10  * version 2 of the License, or (at your option) any later version.
11  *
12  * This library is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  * Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General
18  * Public License along with this library; if not, write to the
19  * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
20  * Boston, MA 02111-1307, USA.
21  *
22  * Author: Alexander Larsson <alexl@redhat.com>
23  */
24
25 #include "config.h"
26 #ifdef HAVE_SPLICE
27 #include <sys/stat.h>
28 #include <unistd.h>
29 #include <fcntl.h>
30 #include <errno.h>
31 #endif
32 #include <string.h>
33 #include <sys/types.h>
34 #ifdef HAVE_PWD_H
35 #include <pwd.h>
36 #endif
37 #include "gfile.h"
38 #include "gvfs.h"
39 #include "gioscheduler.h"
40 #include "gsimpleasyncresult.h"
41 #include "gfileattribute-priv.h"
42 #include "gfiledescriptorbased.h"
43 #include "gpollfilemonitor.h"
44 #include "gappinfo.h"
45 #include "gfileinputstream.h"
46 #include "gfileoutputstream.h"
47 #include "glocalfileoutputstream.h"
48 #include "glocalfileiostream.h"
49 #include "gcancellable.h"
50 #include "gasyncresult.h"
51 #include "gioerror.h"
52 #include "glibintl.h"
53
54
55 /**
56  * SECTION:gfile
57  * @short_description: File and Directory Handling
58  * @include: gio/gio.h
59  * @see_also: #GFileInfo, #GFileEnumerator
60  * 
61  * #GFile is a high level abstraction for manipulating files on a 
62  * virtual file system. #GFile<!-- -->s are lightweight, immutable 
63  * objects that do no I/O upon creation. It is necessary to understand that
64  * #GFile objects do not represent files, merely an identifier for a file. All
65  * file content I/O is implemented as streaming operations (see #GInputStream and 
66  * #GOutputStream).
67  *
68  * To construct a #GFile, you can use: 
69  * g_file_new_for_path() if you have a path.
70  * g_file_new_for_uri() if you have a URI.
71  * g_file_new_for_commandline_arg() for a command line argument.
72  * g_file_new_tmp() to create a temporary file from a template.
73  * g_file_parse_name() from a utf8 string gotten from g_file_get_parse_name().
74  * 
75  * One way to think of a #GFile is as an abstraction of a pathname. For normal
76  * files the system pathname is what is stored internally, but as #GFile<!-- -->s
77  * are extensible it could also be something else that corresponds to a pathname
78  * in a userspace implementation of a filesystem.
79  *
80  * #GFile<!-- -->s make up hierarchies of directories and files that correspond to the
81  * files on a filesystem. You can move through the file system with #GFile using
82  * g_file_get_parent() to get an identifier for the parent directory, g_file_get_child()
83  * to get a child within a directory, g_file_resolve_relative_path() to resolve a relative
84  * path between two #GFile<!-- -->s. There can be multiple hierarchies, so you may not
85  * end up at the same root if you repeatedly call g_file_get_parent() on two different
86  * files.
87  *
88  * All #GFile<!-- -->s have a basename (get with g_file_get_basename()). These names
89  * are byte strings that are used to identify the file on the filesystem (relative to
90  * its parent directory) and there is no guarantees that they have any particular charset
91  * encoding or even make any sense at all. If you want to use filenames in a user
92  * interface you should use the display name that you can get by requesting the
93  * %G_FILE_ATTRIBUTE_STANDARD_DISPLAY_NAME attribute with g_file_query_info().
94  * This is guaranteed to be in utf8 and can be used in a user interface. But always
95  * store the real basename or the #GFile to use to actually access the file, because
96  * there is no way to go from a display name to the actual name.
97  *
98  * Using #GFile as an identifier has the same weaknesses as using a path in that
99  * there may be multiple aliases for the same file. For instance, hard or
100  * soft links may cause two different #GFile<!-- -->s to refer to the same file.
101  * Other possible causes for aliases are: case insensitive filesystems, short
102  * and long names on Fat/NTFS, or bind mounts in Linux. If you want to check if
103  * two #GFile<!-- -->s point to the same file you can query for the
104  * %G_FILE_ATTRIBUTE_ID_FILE attribute. Note that #GFile does some trivial
105  * canonicalization of pathnames passed in, so that trivial differences in the
106  * path string used at creation (duplicated slashes, slash at end of path, "."
107  * or ".." path segments, etc) does not create different #GFile<!-- -->s.
108  * 
109  * Many #GFile operations have both synchronous and asynchronous versions 
110  * to suit your application. Asynchronous versions of synchronous functions 
111  * simply have _async() appended to their function names. The asynchronous 
112  * I/O functions call a #GAsyncReadyCallback which is then used to finalize 
113  * the operation, producing a GAsyncResult which is then passed to the 
114  * function's matching _finish() operation. 
115  *
116  * Some #GFile operations do not have synchronous analogs, as they may
117  * take a very long time to finish, and blocking may leave an application
118  * unusable. Notable cases include:
119  * g_file_mount_mountable() to mount a mountable file.
120  * g_file_unmount_mountable_with_operation() to unmount a mountable file.
121  * g_file_eject_mountable_with_operation() to eject a mountable file.
122  * 
123  * <para id="gfile-etag"><indexterm><primary>entity tag</primary></indexterm>
124  * One notable feature of #GFile<!-- -->s are entity tags, or "etags" for 
125  * short. Entity tags are somewhat like a more abstract version of the 
126  * traditional mtime, and can be used to quickly determine if the file has
127  * been modified from the version on the file system. See the HTTP 1.1 
128  * <ulink url="http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html">specification</ulink>
129  * for HTTP Etag headers, which are a very similar concept.
130  * </para>
131  **/
132
133 static void               g_file_real_query_info_async            (GFile                  *file,
134                                                                    const char             *attributes,
135                                                                    GFileQueryInfoFlags     flags,
136                                                                    int                     io_priority,
137                                                                    GCancellable           *cancellable,
138                                                                    GAsyncReadyCallback     callback,
139                                                                    gpointer                user_data);
140 static GFileInfo *        g_file_real_query_info_finish           (GFile                  *file,
141                                                                    GAsyncResult           *res,
142                                                                    GError                **error);
143 static void               g_file_real_query_filesystem_info_async (GFile                  *file,
144                                                                    const char             *attributes,
145                                                                    int                     io_priority,
146                                                                    GCancellable           *cancellable,
147                                                                    GAsyncReadyCallback     callback,
148                                                                    gpointer                user_data);
149 static GFileInfo *        g_file_real_query_filesystem_info_finish (GFile                  *file,
150                                                                    GAsyncResult           *res,
151                                                                    GError                **error);
152 static void               g_file_real_enumerate_children_async    (GFile                  *file,
153                                                                    const char             *attributes,
154                                                                    GFileQueryInfoFlags     flags,
155                                                                    int                     io_priority,
156                                                                    GCancellable           *cancellable,
157                                                                    GAsyncReadyCallback     callback,
158                                                                    gpointer                user_data);
159 static GFileEnumerator *  g_file_real_enumerate_children_finish   (GFile                  *file,
160                                                                    GAsyncResult           *res,
161                                                                    GError                **error);
162 static void               g_file_real_read_async                  (GFile                  *file,
163                                                                    int                     io_priority,
164                                                                    GCancellable           *cancellable,
165                                                                    GAsyncReadyCallback     callback,
166                                                                    gpointer                user_data);
167 static GFileInputStream * g_file_real_read_finish                 (GFile                  *file,
168                                                                    GAsyncResult           *res,
169                                                                    GError                **error);
170 static void               g_file_real_append_to_async             (GFile                  *file,
171                                                                    GFileCreateFlags        flags,
172                                                                    int                     io_priority,
173                                                                    GCancellable           *cancellable,
174                                                                    GAsyncReadyCallback     callback,
175                                                                    gpointer                user_data);
176 static GFileOutputStream *g_file_real_append_to_finish            (GFile                  *file,
177                                                                    GAsyncResult           *res,
178                                                                    GError                **error);
179 static void               g_file_real_create_async                (GFile                  *file,
180                                                                    GFileCreateFlags        flags,
181                                                                    int                     io_priority,
182                                                                    GCancellable           *cancellable,
183                                                                    GAsyncReadyCallback     callback,
184                                                                    gpointer                user_data);
185 static GFileOutputStream *g_file_real_create_finish               (GFile                  *file,
186                                                                    GAsyncResult           *res,
187                                                                    GError                **error);
188 static void               g_file_real_replace_async               (GFile                  *file,
189                                                                    const char             *etag,
190                                                                    gboolean                make_backup,
191                                                                    GFileCreateFlags        flags,
192                                                                    int                     io_priority,
193                                                                    GCancellable           *cancellable,
194                                                                    GAsyncReadyCallback     callback,
195                                                                    gpointer                user_data);
196 static GFileOutputStream *g_file_real_replace_finish              (GFile                  *file,
197                                                                    GAsyncResult           *res,
198                                                                    GError                **error);
199 static void               g_file_real_open_readwrite_async        (GFile                  *file,
200                                                                    int                  io_priority,
201                                                                    GCancellable           *cancellable,
202                                                                    GAsyncReadyCallback     callback,
203                                                                    gpointer                user_data);
204 static GFileIOStream *    g_file_real_open_readwrite_finish       (GFile                  *file,
205                                                                    GAsyncResult           *res,
206                                                                    GError                **error);
207 static void               g_file_real_create_readwrite_async      (GFile                  *file,
208                                                                    GFileCreateFlags        flags,
209                                                                    int                     io_priority,
210                                                                    GCancellable           *cancellable,
211                                                                    GAsyncReadyCallback     callback,
212                                                                    gpointer                user_data);
213 static GFileIOStream *    g_file_real_create_readwrite_finish     (GFile                  *file,
214                                                                    GAsyncResult           *res,
215                                                                    GError                **error);
216 static void               g_file_real_replace_readwrite_async     (GFile                  *file,
217                                                                    const char             *etag,
218                                                                    gboolean                make_backup,
219                                                                    GFileCreateFlags        flags,
220                                                                    int                     io_priority,
221                                                                    GCancellable           *cancellable,
222                                                                    GAsyncReadyCallback     callback,
223                                                                    gpointer                user_data);
224 static GFileIOStream *    g_file_real_replace_readwrite_finish    (GFile                  *file,
225                                                                   GAsyncResult            *res,
226                                                                   GError                 **error);
227 static gboolean           g_file_real_set_attributes_from_info    (GFile                  *file,
228                                                                    GFileInfo              *info,
229                                                                    GFileQueryInfoFlags     flags,
230                                                                    GCancellable           *cancellable,
231                                                                    GError                **error);
232 static void               g_file_real_set_display_name_async      (GFile                  *file,
233                                                                    const char             *display_name,
234                                                                    int                     io_priority,
235                                                                    GCancellable           *cancellable,
236                                                                    GAsyncReadyCallback     callback,
237                                                                    gpointer                user_data);
238 static GFile *            g_file_real_set_display_name_finish     (GFile                  *file,
239                                                                    GAsyncResult           *res,
240                                                                    GError                **error);
241 static void               g_file_real_set_attributes_async        (GFile                  *file,
242                                                                    GFileInfo              *info,
243                                                                    GFileQueryInfoFlags     flags,
244                                                                    int                     io_priority,
245                                                                    GCancellable           *cancellable,
246                                                                    GAsyncReadyCallback     callback,
247                                                                    gpointer                user_data);
248 static gboolean           g_file_real_set_attributes_finish       (GFile                  *file,
249                                                                    GAsyncResult           *res,
250                                                                    GFileInfo             **info,
251                                                                    GError                **error);
252 static void               g_file_real_find_enclosing_mount_async  (GFile                  *file,
253                                                                    int                     io_priority,
254                                                                    GCancellable           *cancellable,
255                                                                    GAsyncReadyCallback     callback,
256                                                                    gpointer                user_data);
257 static GMount *           g_file_real_find_enclosing_mount_finish (GFile                  *file,
258                                                                    GAsyncResult           *res,
259                                                                    GError                **error);
260 static void               g_file_real_copy_async                  (GFile                  *source,
261                                                                    GFile                  *destination,
262                                                                    GFileCopyFlags          flags,
263                                                                    int                     io_priority,
264                                                                    GCancellable           *cancellable,
265                                                                    GFileProgressCallback   progress_callback,
266                                                                    gpointer                progress_callback_data,
267                                                                    GAsyncReadyCallback     callback,
268                                                                    gpointer                user_data);
269 static gboolean           g_file_real_copy_finish                 (GFile                  *file,
270                                                                    GAsyncResult           *res,
271                                                                    GError                **error);
272
273 typedef GFileIface GFileInterface;
274 G_DEFINE_INTERFACE (GFile, g_file, G_TYPE_OBJECT)
275
276 static void
277 g_file_default_init (GFileIface *iface)
278 {
279   iface->enumerate_children_async = g_file_real_enumerate_children_async;
280   iface->enumerate_children_finish = g_file_real_enumerate_children_finish;
281   iface->set_display_name_async = g_file_real_set_display_name_async;
282   iface->set_display_name_finish = g_file_real_set_display_name_finish;
283   iface->query_info_async = g_file_real_query_info_async;
284   iface->query_info_finish = g_file_real_query_info_finish;
285   iface->query_filesystem_info_async = g_file_real_query_filesystem_info_async;
286   iface->query_filesystem_info_finish = g_file_real_query_filesystem_info_finish;
287   iface->set_attributes_async = g_file_real_set_attributes_async;
288   iface->set_attributes_finish = g_file_real_set_attributes_finish;
289   iface->read_async = g_file_real_read_async;
290   iface->read_finish = g_file_real_read_finish;
291   iface->append_to_async = g_file_real_append_to_async;
292   iface->append_to_finish = g_file_real_append_to_finish;
293   iface->create_async = g_file_real_create_async;
294   iface->create_finish = g_file_real_create_finish;
295   iface->replace_async = g_file_real_replace_async;
296   iface->replace_finish = g_file_real_replace_finish;
297   iface->open_readwrite_async = g_file_real_open_readwrite_async;
298   iface->open_readwrite_finish = g_file_real_open_readwrite_finish;
299   iface->create_readwrite_async = g_file_real_create_readwrite_async;
300   iface->create_readwrite_finish = g_file_real_create_readwrite_finish;
301   iface->replace_readwrite_async = g_file_real_replace_readwrite_async;
302   iface->replace_readwrite_finish = g_file_real_replace_readwrite_finish;
303   iface->find_enclosing_mount_async = g_file_real_find_enclosing_mount_async;
304   iface->find_enclosing_mount_finish = g_file_real_find_enclosing_mount_finish;
305   iface->set_attributes_from_info = g_file_real_set_attributes_from_info;
306   iface->copy_async = g_file_real_copy_async;
307   iface->copy_finish = g_file_real_copy_finish;
308 }
309
310
311 /**
312  * g_file_is_native:
313  * @file: input #GFile.
314  *
315  * Checks to see if a file is native to the platform.
316  *
317  * A native file s one expressed in the platform-native filename format,
318  * e.g. "C:\Windows" or "/usr/bin/". This does not mean the file is local,
319  * as it might be on a locally mounted remote filesystem.
320  *
321  * On some systems non-native files may be available using
322  * the native filesystem via a userspace filesystem (FUSE), in
323  * these cases this call will return %FALSE, but g_file_get_path()
324  * will still return a native path.
325  *
326  * This call does no blocking i/o.
327  * 
328  * Returns: %TRUE if file is native. 
329  **/
330 gboolean
331 g_file_is_native (GFile *file)
332 {
333   GFileIface *iface;
334
335   g_return_val_if_fail (G_IS_FILE (file), FALSE);
336
337   iface = G_FILE_GET_IFACE (file);
338
339   return (* iface->is_native) (file);
340 }
341
342
343 /**
344  * g_file_has_uri_scheme: 
345  * @file: input #GFile.
346  * @uri_scheme: a string containing a URI scheme.
347  *
348  * Checks to see if a #GFile has a given URI scheme.
349  *
350  * This call does no blocking i/o.
351  * 
352  * Returns: %TRUE if #GFile's backend supports the
353  *     given URI scheme, %FALSE if URI scheme is %NULL,
354  *     not supported, or #GFile is invalid.
355  **/
356 gboolean
357 g_file_has_uri_scheme (GFile      *file,
358                        const char *uri_scheme)
359 {
360   GFileIface *iface;
361   
362   g_return_val_if_fail (G_IS_FILE (file), FALSE);
363   g_return_val_if_fail (uri_scheme != NULL, FALSE);
364
365   iface = G_FILE_GET_IFACE (file);
366
367   return (* iface->has_uri_scheme) (file, uri_scheme);
368 }
369
370
371 /**
372  * g_file_get_uri_scheme:
373  * @file: input #GFile.
374  *
375  * Gets the URI scheme for a #GFile.
376  * RFC 3986 decodes the scheme as:
377  * <programlisting>
378  * URI = scheme ":" hier-part [ "?" query ] [ "#" fragment ] 
379  * </programlisting>
380  * Common schemes include "file", "http", "ftp", etc. 
381  *
382  * This call does no blocking i/o.
383  * 
384  * Returns: a string containing the URI scheme for the given 
385  *     #GFile. The returned string should be freed with g_free() 
386  *     when no longer needed.
387  **/
388 char *
389 g_file_get_uri_scheme (GFile *file)
390 {
391   GFileIface *iface;
392
393   g_return_val_if_fail (G_IS_FILE (file), NULL);
394
395   iface = G_FILE_GET_IFACE (file);
396
397   return (* iface->get_uri_scheme) (file);
398 }
399
400
401 /**
402  * g_file_get_basename:
403  * @file: input #GFile.
404  *
405  * Gets the base name (the last component of the path) for a given #GFile.
406  *
407  * If called for the top level of a system (such as the filesystem root
408  * or a uri like sftp://host/) it will return a single directory separator
409  * (and on Windows, possibly a drive letter).
410  *
411  * The base name is a byte string (*not* UTF-8). It has no defined encoding
412  * or rules other than it may not contain zero bytes.  If you want to use
413  * filenames in a user interface you should use the display name that you
414  * can get by requesting the %G_FILE_ATTRIBUTE_STANDARD_DISPLAY_NAME
415  * attribute with g_file_query_info().
416  * 
417  * This call does no blocking i/o.
418  * 
419  * Returns: string containing the #GFile's base name, or %NULL 
420  *     if given #GFile is invalid. The returned string should be 
421  *     freed with g_free() when no longer needed.
422  **/
423 char *
424 g_file_get_basename (GFile *file)
425 {
426   GFileIface *iface;
427   
428   g_return_val_if_fail (G_IS_FILE (file), NULL);
429
430   iface = G_FILE_GET_IFACE (file);
431
432   return (* iface->get_basename) (file);
433 }
434
435 /**
436  * g_file_get_path:
437  * @file: input #GFile.
438  *
439  * Gets the local pathname for #GFile, if one exists. 
440  *
441  * This call does no blocking i/o.
442  * 
443  * Returns: string containing the #GFile's path, or %NULL if 
444  *     no such path exists. The returned string should be 
445  *     freed with g_free() when no longer needed.
446  **/
447 char *
448 g_file_get_path (GFile *file)
449 {
450   GFileIface *iface;
451
452   g_return_val_if_fail (G_IS_FILE (file), NULL);
453
454   iface = G_FILE_GET_IFACE (file);
455
456   return (* iface->get_path) (file);
457 }
458
459 /**
460  * g_file_get_uri:
461  * @file: input #GFile.
462  *
463  * Gets the URI for the @file.
464  *
465  * This call does no blocking i/o.
466  * 
467  * Returns: a string containing the #GFile's URI.
468  *     The returned string should be freed with g_free() when no longer needed.
469  **/
470 char *
471 g_file_get_uri (GFile *file)
472 {
473   GFileIface *iface;
474   
475   g_return_val_if_fail (G_IS_FILE (file), NULL);
476
477   iface = G_FILE_GET_IFACE (file);
478
479   return (* iface->get_uri) (file);
480 }
481
482 /**
483  * g_file_get_parse_name:
484  * @file: input #GFile.
485  *
486  * Gets the parse name of the @file.
487  * A parse name is a UTF-8 string that describes the
488  * file such that one can get the #GFile back using
489  * g_file_parse_name().
490  *
491  * This is generally used to show the #GFile as a nice
492  * full-pathname kind of string in a user interface,
493  * like in a location entry.
494  *
495  * For local files with names that can safely be converted
496  * to UTF8 the pathname is used, otherwise the IRI is used
497  * (a form of URI that allows UTF8 characters unescaped).
498  *
499  * This call does no blocking i/o.
500  * 
501  * Returns: a string containing the #GFile's parse name. The returned 
502  *     string should be freed with g_free() when no longer needed.
503  **/
504 char *
505 g_file_get_parse_name (GFile *file)
506 {
507   GFileIface *iface;
508   
509   g_return_val_if_fail (G_IS_FILE (file), NULL);
510
511   iface = G_FILE_GET_IFACE (file);
512
513   return (* iface->get_parse_name) (file);
514 }
515
516 /**
517  * g_file_dup:
518  * @file: input #GFile.
519  *
520  * Duplicates a #GFile handle. This operation does not duplicate 
521  * the actual file or directory represented by the #GFile; see 
522  * g_file_copy() if attempting to copy a file. 
523  *
524  * This call does no blocking i/o.
525  * 
526  * Returns: (transfer full): a new #GFile that is a duplicate of the given #GFile. 
527  **/
528 GFile *
529 g_file_dup (GFile *file)
530 {
531   GFileIface *iface;
532   
533   g_return_val_if_fail (G_IS_FILE (file), NULL);
534
535   iface = G_FILE_GET_IFACE (file);
536
537   return (* iface->dup) (file);
538 }
539
540 /**
541  * g_file_hash:
542  * @file: (type GFile): #gconstpointer to a #GFile.
543  *
544  * Creates a hash value for a #GFile.
545  *
546  * This call does no blocking i/o.
547  *
548  * Virtual: hash
549  * Returns: 0 if @file is not a valid #GFile, otherwise an 
550  *     integer that can be used as hash value for the #GFile. 
551  *     This function is intended for easily hashing a #GFile to 
552  *     add to a #GHashTable or similar data structure.
553  **/
554 guint
555 g_file_hash (gconstpointer file)
556 {
557   GFileIface *iface;
558   
559   g_return_val_if_fail (G_IS_FILE (file), 0);
560
561   iface = G_FILE_GET_IFACE (file);
562
563   return (* iface->hash) ((GFile *)file);
564 }
565
566 /**
567  * g_file_equal:
568  * @file1: the first #GFile.
569  * @file2: the second #GFile.
570  *
571  * Checks equality of two given #GFile<!-- -->s. Note that two
572  * #GFile<!-- -->s that differ can still refer to the same
573  * file on the filesystem due to various forms of filename
574  * aliasing.
575  *
576  * This call does no blocking i/o.
577  * 
578  * Returns: %TRUE if @file1 and @file2 are equal.
579  *     %FALSE if either is not a #GFile.
580  **/
581 gboolean
582 g_file_equal (GFile *file1,
583               GFile *file2)
584 {
585   GFileIface *iface;
586   
587   g_return_val_if_fail (G_IS_FILE (file1), FALSE);
588   g_return_val_if_fail (G_IS_FILE (file2), FALSE);
589   
590   if (G_TYPE_FROM_INSTANCE (file1) != G_TYPE_FROM_INSTANCE (file2))
591     return FALSE;
592
593   iface = G_FILE_GET_IFACE (file1);
594   
595   return (* iface->equal) (file1, file2);
596 }
597
598
599 /**
600  * g_file_get_parent:
601  * @file: input #GFile.
602  *
603  * Gets the parent directory for the @file. 
604  * If the @file represents the root directory of the 
605  * file system, then %NULL will be returned.
606  *
607  * This call does no blocking i/o.
608  * 
609  * Returns: (transfer full): a #GFile structure to the parent of the given
610  *     #GFile or %NULL if there is no parent. 
611  *     Free the returned object with g_object_unref().
612  **/
613 GFile *
614 g_file_get_parent (GFile *file)
615 {
616   GFileIface *iface;
617   
618   g_return_val_if_fail (G_IS_FILE (file), NULL);
619
620   iface = G_FILE_GET_IFACE (file);
621
622   return (* iface->get_parent) (file);
623 }
624
625 /**
626  * g_file_has_parent:
627  * @file: input #GFile
628  * @parent: the parent to check for, or %NULL
629  *
630  * Checks if @file has a parent, and optionally, if it is @parent.
631  *
632  * If @parent is %NULL then this function returns %TRUE if @file has any
633  * parent at all.  If @parent is non-%NULL then %TRUE is only returned
634  * if @file is a child of @parent.
635  *
636  * Returns: %TRUE if @file is a child of @parent (or any parent in the
637  *          case that @parent is %NULL).
638  *
639  * Since: 2.24
640  **/
641 gboolean
642 g_file_has_parent (GFile *file,
643                    GFile *parent)
644 {
645   GFile *actual_parent;
646   gboolean result;
647
648   g_return_val_if_fail (G_IS_FILE (file), FALSE);
649   g_return_val_if_fail (parent == NULL || G_IS_FILE (parent), FALSE);
650
651   actual_parent = g_file_get_parent (file);
652
653   if (actual_parent != NULL)
654     {
655       if (parent != NULL)
656         result = g_file_equal (parent, actual_parent);
657       else
658         result = TRUE;
659
660       g_object_unref (actual_parent);
661     }
662   else
663     result = FALSE;
664
665   return result;
666 }
667
668 /**
669  * g_file_get_child:
670  * @file: input #GFile.
671  * @name: string containing the child's basename.
672  *
673  * Gets a child of @file with basename equal to @name.
674  *
675  * Note that the file with that specific name might not exist, but
676  * you can still have a #GFile that points to it. You can use this
677  * for instance to create that file.
678  *
679  * This call does no blocking i/o.
680  * 
681  * Returns: (transfer full): a #GFile to a child specified by @name.
682  *     Free the returned object with g_object_unref().
683  **/
684 GFile *
685 g_file_get_child (GFile      *file,
686                   const char *name)
687 {
688   g_return_val_if_fail (G_IS_FILE (file), NULL);
689   g_return_val_if_fail (name != NULL, NULL);
690
691   return g_file_resolve_relative_path (file, name);
692 }
693
694 /**
695  * g_file_get_child_for_display_name:
696  * @file: input #GFile.
697  * @display_name: string to a possible child.
698  * @error: #GError.
699  *
700  * Gets the child of @file for a given @display_name (i.e. a UTF8
701  * version of the name). If this function fails, it returns %NULL and @error will be 
702  * set. This is very useful when constructing a GFile for a new file
703  * and the user entered the filename in the user interface, for instance
704  * when you select a directory and type a filename in the file selector.
705  * 
706  * This call does no blocking i/o.
707  * 
708  * Returns: (transfer full): a #GFile to the specified child, or 
709  *     %NULL if the display name couldn't be converted.  
710  *     Free the returned object with g_object_unref().
711  **/
712 GFile *
713 g_file_get_child_for_display_name (GFile      *file,
714                                    const char *display_name,
715                                    GError **error)
716 {
717   GFileIface *iface;
718   
719   g_return_val_if_fail (G_IS_FILE (file), NULL);
720   g_return_val_if_fail (display_name != NULL, NULL);
721
722   iface = G_FILE_GET_IFACE (file);
723
724   return (* iface->get_child_for_display_name) (file, display_name, error);
725 }
726
727 /**
728  * g_file_has_prefix:
729  * @file: input #GFile.
730  * @prefix: input #GFile.
731  * 
732  * Checks whether @file has the prefix specified by @prefix. In other word, 
733  * if the names of initial elements of @file<!-- -->s pathname match @prefix.
734  * Only full pathname elements are matched, so a path like /foo is not
735  * considered a prefix of /foobar, only of /foo/bar.
736  * 
737  * This call does no i/o, as it works purely on names. As such it can 
738  * sometimes return %FALSE even if @file is inside a @prefix (from a 
739  * filesystem point of view), because the prefix of @file is an alias 
740  * of @prefix.
741  *
742  * Virtual: prefix_matches
743  * Returns:  %TRUE if the @files's parent, grandparent, etc is @prefix. 
744  *     %FALSE otherwise.
745  **/
746 gboolean
747 g_file_has_prefix (GFile *file,
748                    GFile *prefix)
749 {
750   GFileIface *iface;
751   
752   g_return_val_if_fail (G_IS_FILE (file), FALSE);
753   g_return_val_if_fail (G_IS_FILE (prefix), FALSE);
754
755   if (G_TYPE_FROM_INSTANCE (file) != G_TYPE_FROM_INSTANCE (prefix))
756     return FALSE;
757   
758   iface = G_FILE_GET_IFACE (file);
759
760   /* The vtable function differs in arg order since we're
761      using the old contains_file call */
762   return (* iface->prefix_matches) (prefix, file);
763 }
764
765 /**
766  * g_file_get_relative_path:
767  * @parent: input #GFile.
768  * @descendant: input #GFile.
769  *
770  * Gets the path for @descendant relative to @parent. 
771  *
772  * This call does no blocking i/o.
773  * 
774  * Returns: string with the relative path from @descendant 
775  *     to @parent, or %NULL if @descendant doesn't have @parent as prefix. 
776  *     The returned string should be freed with g_free() when no longer needed.
777  **/
778 char *
779 g_file_get_relative_path (GFile *parent,
780                           GFile *descendant)
781 {
782   GFileIface *iface;
783   
784   g_return_val_if_fail (G_IS_FILE (parent), NULL);
785   g_return_val_if_fail (G_IS_FILE (descendant), NULL);
786
787   if (G_TYPE_FROM_INSTANCE (parent) != G_TYPE_FROM_INSTANCE (descendant))
788     return NULL;
789   
790   iface = G_FILE_GET_IFACE (parent);
791
792   return (* iface->get_relative_path) (parent, descendant);
793 }
794
795 /**
796  * g_file_resolve_relative_path:
797  * @file: input #GFile.
798  * @relative_path: a given relative path string.
799  *
800  * Resolves a relative path for @file to an absolute path.
801  *
802  * This call does no blocking i/o.
803  * 
804  * Returns: (transfer full): #GFile to the resolved path. %NULL if @relative_path 
805  *     is %NULL or if @file is invalid.
806  *     Free the returned object with g_object_unref().
807  **/
808 GFile *
809 g_file_resolve_relative_path (GFile      *file,
810                               const char *relative_path)
811 {
812   GFileIface *iface;
813
814   g_return_val_if_fail (G_IS_FILE (file), NULL);
815   g_return_val_if_fail (relative_path != NULL, NULL);
816
817   iface = G_FILE_GET_IFACE (file);
818
819   return (* iface->resolve_relative_path) (file, relative_path);
820 }
821
822 /**
823  * g_file_enumerate_children:
824  * @file: input #GFile.
825  * @attributes: an attribute query string.
826  * @flags: a set of #GFileQueryInfoFlags.
827  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
828  * @error: #GError for error reporting.
829  *
830  * Gets the requested information about the files in a directory. The result
831  * is a #GFileEnumerator object that will give out #GFileInfo objects for
832  * all the files in the directory.
833  *
834  * The @attributes value is a string that specifies the file attributes that
835  * should be gathered. It is not an error if it's not possible to read a particular
836  * requested attribute from a file - it just won't be set. @attributes should
837  * be a comma-separated list of attributes or attribute wildcards. The wildcard "*"
838  * means all attributes, and a wildcard like "standard::*" means all attributes in the standard
839  * namespace. An example attribute query be "standard::*,owner::user".
840  * The standard attributes are available as defines, like #G_FILE_ATTRIBUTE_STANDARD_NAME.
841  *
842  * If @cancellable is not %NULL, then the operation can be cancelled by
843  * triggering the cancellable object from another thread. If the operation
844  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
845  * 
846  * If the file does not exist, the G_IO_ERROR_NOT_FOUND error will be returned.
847  * If the file is not a directory, the G_FILE_ERROR_NOTDIR error will be returned.
848  * Other errors are possible too.
849  *
850  * Returns: (transfer full): A #GFileEnumerator if successful, %NULL on error. 
851  *     Free the returned object with g_object_unref().
852  **/
853 GFileEnumerator *
854 g_file_enumerate_children (GFile                *file,
855                            const char           *attributes,
856                            GFileQueryInfoFlags   flags,
857                            GCancellable         *cancellable,
858                            GError              **error)
859                            
860 {
861   GFileIface *iface;
862   
863   g_return_val_if_fail (G_IS_FILE (file), NULL);
864
865   if (g_cancellable_set_error_if_cancelled (cancellable, error))
866     return NULL;
867   
868   iface = G_FILE_GET_IFACE (file);
869
870   if (iface->enumerate_children == NULL)
871     {
872       g_set_error_literal (error, G_IO_ERROR,
873                            G_IO_ERROR_NOT_SUPPORTED,
874                            _("Operation not supported"));
875       return NULL;
876     }
877
878   return (* iface->enumerate_children) (file, attributes, flags,
879                                         cancellable, error);
880 }
881
882 /**
883  * g_file_enumerate_children_async:
884  * @file: input #GFile.
885  * @attributes: an attribute query string.
886  * @flags: a set of #GFileQueryInfoFlags.
887  * @io_priority: the <link linkend="io-priority">I/O priority</link> 
888  *     of the request.
889  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
890  * @callback: (scope async): a #GAsyncReadyCallback to call when the
891  *     request is satisfied
892  * @user_data: (closure): the data to pass to callback function
893  *
894  * Asynchronously gets the requested information about the files in a directory. The result
895  * is a #GFileEnumerator object that will give out #GFileInfo objects for
896  * all the files in the directory.
897  *
898  * For more details, see g_file_enumerate_children() which is
899  * the synchronous version of this call.
900  *
901  * When the operation is finished, @callback will be called. You can then call
902  * g_file_enumerate_children_finish() to get the result of the operation.
903  **/
904 void
905 g_file_enumerate_children_async (GFile               *file,
906                                  const char          *attributes,
907                                  GFileQueryInfoFlags  flags,
908                                  int                  io_priority,
909                                  GCancellable        *cancellable,
910                                  GAsyncReadyCallback  callback,
911                                  gpointer             user_data)
912 {
913   GFileIface *iface;
914
915   g_return_if_fail (G_IS_FILE (file));
916
917   iface = G_FILE_GET_IFACE (file);
918   (* iface->enumerate_children_async) (file,
919                                        attributes,
920                                        flags,
921                                        io_priority,
922                                        cancellable,
923                                        callback,
924                                        user_data);
925 }
926
927 /**
928  * g_file_enumerate_children_finish:
929  * @file: input #GFile.
930  * @res: a #GAsyncResult.
931  * @error: a #GError.
932  * 
933  * Finishes an async enumerate children operation.
934  * See g_file_enumerate_children_async().
935  *
936  * Returns: (transfer full): a #GFileEnumerator or %NULL if an error occurred.
937  *     Free the returned object with g_object_unref().
938  **/
939 GFileEnumerator *
940 g_file_enumerate_children_finish (GFile         *file,
941                                   GAsyncResult  *res,
942                                   GError       **error)
943 {
944   GFileIface *iface;
945   
946   g_return_val_if_fail (G_IS_FILE (file), NULL);
947   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), NULL);
948
949   if (G_IS_SIMPLE_ASYNC_RESULT (res))
950     {
951       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
952       if (g_simple_async_result_propagate_error (simple, error))
953         return NULL;
954     }
955   
956   iface = G_FILE_GET_IFACE (file);
957   return (* iface->enumerate_children_finish) (file, res, error);
958 }
959
960 /**
961  * g_file_query_exists:
962  * @file: input #GFile.
963  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
964  *
965  * Utility function to check if a particular file exists. This is
966  * implemented using g_file_query_info() and as such does blocking I/O.
967  *
968  * Note that in many cases it is racy to first check for file existence
969  * and then execute something based on the outcome of that, because the
970  * file might have been created or removed in between the operations. The
971  * general approach to handling that is to not check, but just do the
972  * operation and handle the errors as they come.
973  *
974  * As an example of race-free checking, take the case of reading a file, and
975  * if it doesn't exist, creating it. There are two racy versions: read it, and
976  * on error create it; and: check if it exists, if not create it. These
977  * can both result in two processes creating the file (with perhaps a partially
978  * written file as the result). The correct approach is to always try to create
979  * the file with g_file_create() which will either atomically create the file
980  * or fail with a G_IO_ERROR_EXISTS error.
981  *
982  * However, in many cases an existence check is useful in a user
983  * interface, for instance to make a menu item sensitive/insensitive, so that
984  * you don't have to fool users that something is possible and then just show
985  * and error dialog. If you do this, you should make sure to also handle the
986  * errors that can happen due to races when you execute the operation.
987  * 
988  * Returns: %TRUE if the file exists (and can be detected without error), %FALSE otherwise (or if cancelled).
989  */
990 gboolean
991 g_file_query_exists (GFile *file,
992                      GCancellable *cancellable)
993 {
994   GFileInfo *info;
995   
996   g_return_val_if_fail (G_IS_FILE(file), FALSE);
997   
998   info = g_file_query_info (file, G_FILE_ATTRIBUTE_STANDARD_TYPE,
999                             G_FILE_QUERY_INFO_NONE, cancellable, NULL);
1000   if (info != NULL)
1001     {
1002       g_object_unref (info);
1003       return TRUE;
1004     }
1005   
1006   return FALSE;
1007 }
1008
1009 /**
1010  * g_file_query_file_type:
1011  * @file: input #GFile.
1012  * @flags: a set of #GFileQueryInfoFlags passed to g_file_query_info().
1013  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
1014  *
1015  * Utility function to inspect the #GFileType of a file. This is
1016  * implemented using g_file_query_info() and as such does blocking I/O.
1017  *
1018  * The primary use case of this method is to check if a file is a regular file,
1019  * directory, or symlink.
1020  * 
1021  * Returns: The #GFileType of the file and #G_FILE_TYPE_UNKNOWN if the file
1022  *          does not exist
1023  *
1024  * Since: 2.18
1025  */
1026 GFileType
1027 g_file_query_file_type (GFile *file,
1028                         GFileQueryInfoFlags   flags,
1029                         GCancellable *cancellable)
1030 {
1031   GFileInfo *info;
1032   GFileType file_type;
1033   
1034   g_return_val_if_fail (G_IS_FILE(file), G_FILE_TYPE_UNKNOWN);
1035   info = g_file_query_info (file, G_FILE_ATTRIBUTE_STANDARD_TYPE, flags,
1036                             cancellable, NULL);
1037   if (info != NULL)
1038     {
1039       file_type = g_file_info_get_file_type (info);
1040       g_object_unref (info);
1041     }
1042   else
1043     file_type = G_FILE_TYPE_UNKNOWN;
1044   
1045   return file_type;
1046 }
1047
1048 /**
1049  * g_file_query_info:
1050  * @file: input #GFile.
1051  * @attributes: an attribute query string.
1052  * @flags: a set of #GFileQueryInfoFlags.
1053  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
1054  * @error: a #GError.
1055  *
1056  * Gets the requested information about specified @file. The result
1057  * is a #GFileInfo object that contains key-value attributes (such as 
1058  * the type or size of the file).
1059  *
1060  * The @attributes value is a string that specifies the file attributes that
1061  * should be gathered. It is not an error if it's not possible to read a particular
1062  * requested attribute from a file - it just won't be set. @attributes should
1063  * be a comma-separated list of attributes or attribute wildcards. The wildcard "*"
1064  * means all attributes, and a wildcard like "standard::*" means all attributes in the standard
1065  * namespace. An example attribute query be "standard::*,owner::user".
1066  * The standard attributes are available as defines, like #G_FILE_ATTRIBUTE_STANDARD_NAME.
1067  * 
1068  * If @cancellable is not %NULL, then the operation can be cancelled by
1069  * triggering the cancellable object from another thread. If the operation
1070  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
1071  *
1072  * For symlinks, normally the information about the target of the
1073  * symlink is returned, rather than information about the symlink itself.
1074  * However if you pass #G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS in @flags the
1075  * information about the symlink itself will be returned. Also, for symlinks
1076  * that point to non-existing files the information about the symlink itself
1077  * will be returned.
1078  *
1079  * If the file does not exist, the G_IO_ERROR_NOT_FOUND error will be returned.
1080  * Other errors are possible too, and depend on what kind of filesystem the file is on.
1081  *
1082  * Returns: (transfer full): a #GFileInfo for the given @file, or %NULL on error.
1083  *     Free the returned object with g_object_unref().
1084  **/
1085 GFileInfo *
1086 g_file_query_info (GFile                *file,
1087                    const char           *attributes,
1088                    GFileQueryInfoFlags   flags,
1089                    GCancellable         *cancellable,
1090                    GError              **error)
1091 {
1092   GFileIface *iface;
1093   
1094   g_return_val_if_fail (G_IS_FILE (file), NULL);
1095
1096   if (g_cancellable_set_error_if_cancelled (cancellable, error))
1097     return NULL;
1098   
1099   iface = G_FILE_GET_IFACE (file);
1100
1101   if (iface->query_info == NULL)
1102     {
1103       g_set_error_literal (error, G_IO_ERROR,
1104                            G_IO_ERROR_NOT_SUPPORTED,
1105                            _("Operation not supported"));
1106       return NULL;
1107     }
1108   
1109   return (* iface->query_info) (file, attributes, flags, cancellable, error);
1110 }
1111
1112 /**
1113  * g_file_query_info_async:
1114  * @file: input #GFile.
1115  * @attributes: an attribute query string.
1116  * @flags: a set of #GFileQueryInfoFlags.
1117  * @io_priority: the <link linkend="io-priority">I/O priority</link> 
1118  *     of the request.
1119  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore. 
1120  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied
1121  * @user_data: (closure): the data to pass to callback function
1122  * 
1123  * Asynchronously gets the requested information about specified @file. The result
1124  * is a #GFileInfo object that contains key-value attributes (such as type or size
1125  * for the file).
1126  * 
1127  * For more details, see g_file_query_info() which is
1128  * the synchronous version of this call.
1129  *
1130  * When the operation is finished, @callback will be called. You can then call
1131  * g_file_query_info_finish() to get the result of the operation.
1132  **/
1133 void
1134 g_file_query_info_async (GFile               *file,
1135                          const char          *attributes,
1136                          GFileQueryInfoFlags  flags,
1137                          int                  io_priority,
1138                          GCancellable        *cancellable,
1139                          GAsyncReadyCallback  callback,
1140                          gpointer             user_data)
1141 {
1142   GFileIface *iface;
1143   
1144   g_return_if_fail (G_IS_FILE (file));
1145
1146   iface = G_FILE_GET_IFACE (file);
1147   (* iface->query_info_async) (file,
1148                                attributes,
1149                                flags,
1150                                io_priority,
1151                                cancellable,
1152                                callback,
1153                                user_data);
1154 }
1155
1156 /**
1157  * g_file_query_info_finish:
1158  * @file: input #GFile.
1159  * @res: a #GAsyncResult. 
1160  * @error: a #GError. 
1161  * 
1162  * Finishes an asynchronous file info query. 
1163  * See g_file_query_info_async().
1164  * 
1165  * Returns: (transfer full): #GFileInfo for given @file or %NULL on error.
1166  *     Free the returned object with g_object_unref().
1167  **/
1168 GFileInfo *
1169 g_file_query_info_finish (GFile         *file,
1170                           GAsyncResult  *res,
1171                           GError       **error)
1172 {
1173   GFileIface *iface;
1174
1175   g_return_val_if_fail (G_IS_FILE (file), NULL);
1176   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), NULL);
1177
1178   if (G_IS_SIMPLE_ASYNC_RESULT (res))
1179     {
1180       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
1181       if (g_simple_async_result_propagate_error (simple, error))
1182         return NULL;
1183     }
1184   
1185   iface = G_FILE_GET_IFACE (file);
1186   return (* iface->query_info_finish) (file, res, error);
1187 }
1188
1189 /**
1190  * g_file_query_filesystem_info:
1191  * @file: input #GFile.
1192  * @attributes:  an attribute query string.
1193  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore. 
1194  * @error: a #GError. 
1195  * 
1196  * Similar to g_file_query_info(), but obtains information
1197  * about the filesystem the @file is on, rather than the file itself.
1198  * For instance the amount of space available and the type of
1199  * the filesystem.
1200  *
1201  * The @attributes value is a string that specifies the file attributes that
1202  * should be gathered. It is not an error if it's not possible to read a particular
1203  * requested attribute from a file - it just won't be set. @attributes should
1204  * be a comma-separated list of attributes or attribute wildcards. The wildcard "*"
1205  * means all attributes, and a wildcard like "filesystem::*" means all attributes in the
1206  * filesystem namespace. The standard namespace for filesystem attributes is "filesystem".
1207  * Common attributes of interest are #G_FILE_ATTRIBUTE_FILESYSTEM_SIZE
1208  * (the total size of the filesystem in bytes), #G_FILE_ATTRIBUTE_FILESYSTEM_FREE (number of
1209  * bytes available), and #G_FILE_ATTRIBUTE_FILESYSTEM_TYPE (type of the filesystem).
1210  * 
1211  * If @cancellable is not %NULL, then the operation can be cancelled by
1212  * triggering the cancellable object from another thread. If the operation
1213  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
1214  *
1215  * If the file does not exist, the G_IO_ERROR_NOT_FOUND error will be returned.
1216  * Other errors are possible too, and depend on what kind of filesystem the file is on.
1217  *
1218  * Returns: (transfer full): a #GFileInfo or %NULL if there was an error.
1219  *     Free the returned object with g_object_unref().
1220  **/
1221 GFileInfo *
1222 g_file_query_filesystem_info (GFile         *file,
1223                               const char    *attributes,
1224                               GCancellable  *cancellable,
1225                               GError       **error)
1226 {
1227   GFileIface *iface;
1228   
1229   g_return_val_if_fail (G_IS_FILE (file), NULL);
1230
1231   if (g_cancellable_set_error_if_cancelled (cancellable, error))
1232     return NULL;
1233   
1234   iface = G_FILE_GET_IFACE (file);
1235
1236   if (iface->query_filesystem_info == NULL)
1237     {
1238       g_set_error_literal (error, G_IO_ERROR,
1239                            G_IO_ERROR_NOT_SUPPORTED,
1240                            _("Operation not supported"));
1241       return NULL;
1242     }
1243   
1244   return (* iface->query_filesystem_info) (file, attributes, cancellable, error);
1245 }
1246
1247 /**
1248  * g_file_query_filesystem_info_async:
1249  * @file: input #GFile.
1250  * @attributes: an attribute query string.
1251  * @io_priority: the <link linkend="io-priority">I/O priority</link> 
1252  *     of the request.
1253  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore. 
1254  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied
1255  * @user_data: (closure): the data to pass to callback function
1256  * 
1257  * Asynchronously gets the requested information about the filesystem
1258  * that the specified @file is on. The result is a #GFileInfo object
1259  * that contains key-value attributes (such as type or size for the
1260  * file).
1261  * 
1262  * For more details, see g_file_query_filesystem_info() which is the
1263  * synchronous version of this call.
1264  *
1265  * When the operation is finished, @callback will be called. You can
1266  * then call g_file_query_info_finish() to get the result of the
1267  * operation.
1268  **/
1269 void
1270 g_file_query_filesystem_info_async (GFile               *file,
1271                                     const char          *attributes,
1272                                     int                  io_priority,
1273                                     GCancellable        *cancellable,
1274                                     GAsyncReadyCallback  callback,
1275                                     gpointer             user_data)
1276 {
1277   GFileIface *iface;
1278   
1279   g_return_if_fail (G_IS_FILE (file));
1280
1281   iface = G_FILE_GET_IFACE (file);
1282   (* iface->query_filesystem_info_async) (file,
1283                                           attributes,
1284                                           io_priority,
1285                                           cancellable,
1286                                           callback,
1287                                           user_data);
1288 }
1289
1290 /**
1291  * g_file_query_filesystem_info_finish:
1292  * @file: input #GFile.
1293  * @res: a #GAsyncResult. 
1294  * @error: a #GError. 
1295  * 
1296  * Finishes an asynchronous filesystem info query.  See
1297  * g_file_query_filesystem_info_async().
1298  * 
1299  * Returns: (transfer full): #GFileInfo for given @file or %NULL on error.
1300  *     Free the returned object with g_object_unref().
1301  **/
1302 GFileInfo *
1303 g_file_query_filesystem_info_finish (GFile         *file,
1304                                      GAsyncResult  *res,
1305                                      GError       **error)
1306 {
1307   GFileIface *iface;
1308
1309   g_return_val_if_fail (G_IS_FILE (file), NULL);
1310   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), NULL);
1311
1312   if (G_IS_SIMPLE_ASYNC_RESULT (res))
1313     {
1314       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
1315       if (g_simple_async_result_propagate_error (simple, error))
1316         return NULL;
1317     }
1318   
1319   iface = G_FILE_GET_IFACE (file);
1320   return (* iface->query_filesystem_info_finish) (file, res, error);
1321 }
1322
1323 /**
1324  * g_file_find_enclosing_mount:
1325  * @file: input #GFile.
1326  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore. 
1327  * @error: a #GError. 
1328  *
1329  * Gets a #GMount for the #GFile. 
1330  *
1331  * If the #GFileIface for @file does not have a mount (e.g. possibly a 
1332  * remote share), @error will be set to %G_IO_ERROR_NOT_FOUND and %NULL
1333  * will be returned.
1334  * 
1335  * If @cancellable is not %NULL, then the operation can be cancelled by
1336  * triggering the cancellable object from another thread. If the operation
1337  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
1338  * 
1339  * Returns: (transfer full): a #GMount where the @file is located or %NULL on error.
1340  *     Free the returned object with g_object_unref().
1341  **/
1342 GMount *
1343 g_file_find_enclosing_mount (GFile         *file,
1344                              GCancellable  *cancellable,
1345                              GError       **error)
1346 {
1347   GFileIface *iface;
1348
1349   g_return_val_if_fail (G_IS_FILE (file), NULL);
1350
1351   if (g_cancellable_set_error_if_cancelled (cancellable, error))
1352     return NULL;
1353
1354   iface = G_FILE_GET_IFACE (file);
1355   if (iface->find_enclosing_mount == NULL)
1356     {
1357
1358       g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND,
1359                         /* Translators: This is an error message when trying to find the
1360                          * enclosing (user visible) mount of a file, but none exists. */
1361                    _("Containing mount does not exist"));
1362       return NULL;
1363     }
1364
1365   return (* iface->find_enclosing_mount) (file, cancellable, error);
1366 }
1367
1368 /**
1369  * g_file_find_enclosing_mount_async:
1370  * @file: a #GFile
1371  * @io_priority: the <link linkend="io-priority">I/O priority</link> 
1372  *     of the request.
1373  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
1374  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied
1375  * @user_data: (closure): the data to pass to callback function
1376  *
1377  * Asynchronously gets the mount for the file.
1378  *
1379  * For more details, see g_file_find_enclosing_mount() which is
1380  * the synchronous version of this call.
1381  *
1382  * When the operation is finished, @callback will be called. You can then call
1383  * g_file_find_enclosing_mount_finish() to get the result of the operation.
1384  */
1385 void
1386 g_file_find_enclosing_mount_async (GFile              *file,
1387                                    int                   io_priority,
1388                                    GCancellable         *cancellable,
1389                                    GAsyncReadyCallback   callback,
1390                                    gpointer              user_data)
1391 {
1392   GFileIface *iface;
1393
1394   g_return_if_fail (G_IS_FILE (file));
1395
1396   iface = G_FILE_GET_IFACE (file);
1397   (* iface->find_enclosing_mount_async) (file,
1398                                          io_priority,
1399                                          cancellable,
1400                                          callback,
1401                                          user_data);
1402 }
1403
1404 /**
1405  * g_file_find_enclosing_mount_finish:
1406  * @file: a #GFile
1407  * @res: a #GAsyncResult
1408  * @error: a #GError
1409  * 
1410  * Finishes an asynchronous find mount request. 
1411  * See g_file_find_enclosing_mount_async().
1412  * 
1413  * Returns: (transfer full): #GMount for given @file or %NULL on error.
1414  *     Free the returned object with g_object_unref().
1415  **/
1416 GMount *
1417 g_file_find_enclosing_mount_finish (GFile         *file,
1418                                     GAsyncResult  *res,
1419                                     GError       **error)
1420 {
1421   GFileIface *iface;
1422   
1423   g_return_val_if_fail (G_IS_FILE (file), NULL);
1424   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), NULL);
1425
1426   if (G_IS_SIMPLE_ASYNC_RESULT (res))
1427     {
1428       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
1429       if (g_simple_async_result_propagate_error (simple, error))
1430         return NULL;
1431     }
1432   
1433   iface = G_FILE_GET_IFACE (file);
1434   return (* iface->find_enclosing_mount_finish) (file, res, error);
1435 }
1436
1437
1438 /**
1439  * g_file_read:
1440  * @file: #GFile to read.
1441  * @cancellable: (allow-none): a #GCancellable
1442  * @error: a #GError, or %NULL
1443  *
1444  * Opens a file for reading. The result is a #GFileInputStream that
1445  * can be used to read the contents of the file.
1446  *
1447  * If @cancellable is not %NULL, then the operation can be cancelled by
1448  * triggering the cancellable object from another thread. If the operation
1449  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
1450  * 
1451  * If the file does not exist, the G_IO_ERROR_NOT_FOUND error will be returned.
1452  * If the file is a directory, the G_IO_ERROR_IS_DIRECTORY error will be returned.
1453  * Other errors are possible too, and depend on what kind of filesystem the file is on.
1454  *
1455  * Virtual: read_fn
1456  * Returns: (transfer full): #GFileInputStream or %NULL on error.
1457  *     Free the returned object with g_object_unref().
1458  **/
1459 GFileInputStream *
1460 g_file_read (GFile         *file,
1461              GCancellable  *cancellable,
1462              GError       **error)
1463 {
1464   GFileIface *iface;
1465   
1466   g_return_val_if_fail (G_IS_FILE (file), NULL);
1467
1468   if (g_cancellable_set_error_if_cancelled (cancellable, error))
1469     return NULL;
1470
1471   iface = G_FILE_GET_IFACE (file);
1472
1473   if (iface->read_fn == NULL)
1474     {
1475       g_set_error_literal (error, G_IO_ERROR,
1476                            G_IO_ERROR_NOT_SUPPORTED,
1477                            _("Operation not supported"));
1478       return NULL;
1479     }
1480   
1481   return (* iface->read_fn) (file, cancellable, error);
1482 }
1483
1484 /**
1485  * g_file_append_to:
1486  * @file: input #GFile.
1487  * @flags: a set of #GFileCreateFlags.
1488  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
1489  * @error: a #GError, or %NULL
1490  *
1491  * Gets an output stream for appending data to the file. If
1492  * the file doesn't already exist it is created.
1493  *
1494  * By default files created are generally readable by everyone,
1495  * but if you pass #G_FILE_CREATE_PRIVATE in @flags the file
1496  * will be made readable only to the current user, to the level that
1497  * is supported on the target filesystem.
1498  *
1499  * If @cancellable is not %NULL, then the operation can be cancelled by
1500  * triggering the cancellable object from another thread. If the operation
1501  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
1502  *
1503  * Some file systems don't allow all file names, and may
1504  * return an %G_IO_ERROR_INVALID_FILENAME error.
1505  * If the file is a directory the %G_IO_ERROR_IS_DIRECTORY error will be
1506  * returned. Other errors are possible too, and depend on what kind of
1507  * filesystem the file is on.
1508  * 
1509  * Returns: (transfer full): a #GFileOutputStream, or %NULL on error.
1510  *     Free the returned object with g_object_unref().
1511  **/
1512 GFileOutputStream *
1513 g_file_append_to (GFile             *file,
1514                   GFileCreateFlags   flags,
1515                   GCancellable      *cancellable,
1516                   GError           **error)
1517 {
1518   GFileIface *iface;
1519
1520   g_return_val_if_fail (G_IS_FILE (file), NULL);
1521
1522   if (g_cancellable_set_error_if_cancelled (cancellable, error))
1523     return NULL;
1524   
1525   iface = G_FILE_GET_IFACE (file);
1526
1527   if (iface->append_to == NULL)
1528     {
1529       g_set_error_literal (error, G_IO_ERROR,
1530                            G_IO_ERROR_NOT_SUPPORTED,
1531                            _("Operation not supported"));
1532       return NULL;
1533     }
1534   
1535   return (* iface->append_to) (file, flags, cancellable, error);
1536 }
1537
1538 /**
1539  * g_file_create:
1540  * @file: input #GFile.
1541  * @flags: a set of #GFileCreateFlags.
1542  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
1543  * @error: a #GError, or %NULL
1544  *
1545  * Creates a new file and returns an output stream for writing to it.
1546  * The file must not already exist.
1547  *
1548  * By default files created are generally readable by everyone,
1549  * but if you pass #G_FILE_CREATE_PRIVATE in @flags the file
1550  * will be made readable only to the current user, to the level that
1551  * is supported on the target filesystem.
1552  *
1553  * If @cancellable is not %NULL, then the operation can be cancelled by
1554  * triggering the cancellable object from another thread. If the operation
1555  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
1556  *
1557  * If a file or directory with this name already exists the G_IO_ERROR_EXISTS
1558  * error will be returned.
1559  * Some file systems don't allow all file names, and may
1560  * return an G_IO_ERROR_INVALID_FILENAME error, and if the name
1561  * is to long G_IO_ERROR_FILENAME_TOO_LONG will be returned.
1562  * Other errors are possible too, and depend on what kind of
1563  * filesystem the file is on.
1564  * 
1565  * Returns: (transfer full): a #GFileOutputStream for the newly created file, or 
1566  *     %NULL on error.
1567  *     Free the returned object with g_object_unref().
1568  **/
1569 GFileOutputStream *
1570 g_file_create (GFile             *file,
1571                GFileCreateFlags   flags,
1572                GCancellable      *cancellable,
1573                GError           **error)
1574 {
1575   GFileIface *iface;
1576   
1577   g_return_val_if_fail (G_IS_FILE (file), NULL);
1578
1579   if (g_cancellable_set_error_if_cancelled (cancellable, error))
1580     return NULL;
1581   
1582   iface = G_FILE_GET_IFACE (file);
1583
1584   if (iface->create == NULL)
1585     {
1586       g_set_error_literal (error, G_IO_ERROR,
1587                            G_IO_ERROR_NOT_SUPPORTED,
1588                            _("Operation not supported"));
1589       return NULL;
1590     }
1591   
1592   return (* iface->create) (file, flags, cancellable, error);
1593 }
1594
1595 /**
1596  * g_file_replace:
1597  * @file: input #GFile.
1598  * @etag: (allow-none): an optional <link linkend="gfile-etag">entity tag</link> for the 
1599  *     current #GFile, or #NULL to ignore.
1600  * @make_backup: %TRUE if a backup should be created.
1601  * @flags: a set of #GFileCreateFlags.
1602  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
1603  * @error: a #GError, or %NULL
1604  *
1605  * Returns an output stream for overwriting the file, possibly
1606  * creating a backup copy of the file first. If the file doesn't exist,
1607  * it will be created.
1608  *
1609  * This will try to replace the file in the safest way possible so
1610  * that any errors during the writing will not affect an already
1611  * existing copy of the file. For instance, for local files it
1612  * may write to a temporary file and then atomically rename over
1613  * the destination when the stream is closed.
1614  * 
1615  * By default files created are generally readable by everyone,
1616  * but if you pass #G_FILE_CREATE_PRIVATE in @flags the file
1617  * will be made readable only to the current user, to the level that
1618  * is supported on the target filesystem.
1619  *
1620  * If @cancellable is not %NULL, then the operation can be cancelled by
1621  * triggering the cancellable object from another thread. If the operation
1622  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
1623  * 
1624  * If you pass in a non-#NULL @etag value, then this value is
1625  * compared to the current entity tag of the file, and if they differ
1626  * an G_IO_ERROR_WRONG_ETAG error is returned. This generally means
1627  * that the file has been changed since you last read it. You can get
1628  * the new etag from g_file_output_stream_get_etag() after you've
1629  * finished writing and closed the #GFileOutputStream. When you load
1630  * a new file you can use g_file_input_stream_query_info() to get
1631  * the etag of the file.
1632  * 
1633  * If @make_backup is %TRUE, this function will attempt to make a backup
1634  * of the current file before overwriting it. If this fails a G_IO_ERROR_CANT_CREATE_BACKUP
1635  * error will be returned. If you want to replace anyway, try again with
1636  * @make_backup set to %FALSE.
1637  *
1638  * If the file is a directory the G_IO_ERROR_IS_DIRECTORY error will be returned,
1639  * and if the file is some other form of non-regular file then a
1640  * G_IO_ERROR_NOT_REGULAR_FILE error will be returned.
1641  * Some file systems don't allow all file names, and may
1642  * return an G_IO_ERROR_INVALID_FILENAME error, and if the name
1643  * is to long G_IO_ERROR_FILENAME_TOO_LONG will be returned.
1644  * Other errors are possible too, and depend on what kind of
1645  * filesystem the file is on.
1646  *
1647  * Returns: (transfer full): a #GFileOutputStream or %NULL on error. 
1648  *     Free the returned object with g_object_unref().
1649  **/
1650 GFileOutputStream *
1651 g_file_replace (GFile             *file,
1652                 const char        *etag,
1653                 gboolean           make_backup,
1654                 GFileCreateFlags   flags,
1655                 GCancellable      *cancellable,
1656                 GError           **error)
1657 {
1658   GFileIface *iface;
1659
1660   g_return_val_if_fail (G_IS_FILE (file), NULL);
1661
1662   if (g_cancellable_set_error_if_cancelled (cancellable, error))
1663     return NULL;
1664   
1665   iface = G_FILE_GET_IFACE (file);
1666
1667   if (iface->replace == NULL)
1668     {
1669       g_set_error_literal (error, G_IO_ERROR,
1670                            G_IO_ERROR_NOT_SUPPORTED,
1671                            _("Operation not supported"));
1672       return NULL;
1673     }
1674   
1675   
1676   /* Handle empty tag string as NULL in consistent way. */
1677   if (etag && *etag == 0)
1678     etag = NULL;
1679   
1680   return (* iface->replace) (file, etag, make_backup, flags, cancellable, error);
1681 }
1682
1683 /**
1684  * g_file_open_readwrite:
1685  * @file: #GFile to open
1686  * @cancellable: (allow-none): a #GCancellable
1687  * @error: a #GError, or %NULL
1688  *
1689  * Opens an existing file for reading and writing. The result is
1690  * a #GFileIOStream that can be used to read and write the contents of the file.
1691  *
1692  * If @cancellable is not %NULL, then the operation can be cancelled by
1693  * triggering the cancellable object from another thread. If the operation
1694  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
1695  *
1696  * If the file does not exist, the G_IO_ERROR_NOT_FOUND error will be returned.
1697  * If the file is a directory, the G_IO_ERROR_IS_DIRECTORY error will be returned.
1698  * Other errors are possible too, and depend on what kind of filesystem the file is on.
1699  * Note that in many non-local file cases read and write streams are not supported,
1700  * so make sure you really need to do read and write streaming, rather than
1701  * just opening for reading or writing.
1702  *
1703  * Returns: (transfer full): #GFileIOStream or %NULL on error.
1704  *     Free the returned object with g_object_unref().
1705  *
1706  * Since: 2.22
1707  **/
1708 GFileIOStream *
1709 g_file_open_readwrite (GFile                      *file,
1710                        GCancellable               *cancellable,
1711                        GError                    **error)
1712 {
1713   GFileIface *iface;
1714
1715   g_return_val_if_fail (G_IS_FILE (file), NULL);
1716
1717   if (g_cancellable_set_error_if_cancelled (cancellable, error))
1718     return NULL;
1719
1720   iface = G_FILE_GET_IFACE (file);
1721
1722   if (iface->open_readwrite == NULL)
1723     {
1724       g_set_error_literal (error, G_IO_ERROR,
1725                            G_IO_ERROR_NOT_SUPPORTED,
1726                            _("Operation not supported"));
1727       return NULL;
1728     }
1729
1730   return (* iface->open_readwrite) (file, cancellable, error);
1731 }
1732
1733 /**
1734  * g_file_create_readwrite:
1735  * @file: a #GFile
1736  * @flags: a set of #GFileCreateFlags
1737  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore
1738  * @error: return location for a #GError, or %NULL
1739  *
1740  * Creates a new file and returns a stream for reading and writing to it.
1741  * The file must not already exist.
1742  *
1743  * By default files created are generally readable by everyone,
1744  * but if you pass #G_FILE_CREATE_PRIVATE in @flags the file
1745  * will be made readable only to the current user, to the level that
1746  * is supported on the target filesystem.
1747  *
1748  * If @cancellable is not %NULL, then the operation can be cancelled by
1749  * triggering the cancellable object from another thread. If the operation
1750  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
1751  *
1752  * If a file or directory with this name already exists the %G_IO_ERROR_EXISTS
1753  * error will be returned. Some file systems don't allow all file names,
1754  * and may return an %G_IO_ERROR_INVALID_FILENAME error, and if the name
1755  * is too long, %G_IO_ERROR_FILENAME_TOO_LONG will be returned. Other errors
1756  * are possible too, and depend on what kind of filesystem the file is on.
1757  *
1758  * Note that in many non-local file cases read and write streams are not
1759  * supported, so make sure you really need to do read and write streaming,
1760  * rather than just opening for reading or writing.
1761  *
1762  * Returns: (transfer full): a #GFileIOStream for the newly created file, or %NULL on error.
1763  *     Free the returned object with g_object_unref().
1764  *
1765  * Since: 2.22
1766  */
1767 GFileIOStream *
1768 g_file_create_readwrite (GFile             *file,
1769                          GFileCreateFlags   flags,
1770                          GCancellable      *cancellable,
1771                          GError           **error)
1772 {
1773   GFileIface *iface;
1774
1775   g_return_val_if_fail (G_IS_FILE (file), NULL);
1776
1777   if (g_cancellable_set_error_if_cancelled (cancellable, error))
1778     return NULL;
1779
1780   iface = G_FILE_GET_IFACE (file);
1781
1782   if (iface->create_readwrite == NULL)
1783     {
1784       g_set_error_literal (error, G_IO_ERROR,
1785                            G_IO_ERROR_NOT_SUPPORTED,
1786                            _("Operation not supported"));
1787       return NULL;
1788     }
1789
1790   return (* iface->create_readwrite) (file, flags, cancellable, error);
1791 }
1792
1793 /**
1794  * g_file_replace_readwrite:
1795  * @file: a #GFile
1796  * @etag: (allow-none): an optional <link linkend="gfile-etag">entity tag</link> for the
1797  *     current #GFile, or #NULL to ignore
1798  * @make_backup: %TRUE if a backup should be created
1799  * @flags: a set of #GFileCreateFlags
1800  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore
1801  * @error: return location for a #GError, or %NULL
1802  *
1803  * Returns an output stream for overwriting the file in readwrite mode,
1804  * possibly creating a backup copy of the file first. If the file doesn't
1805  * exist, it will be created.
1806  *
1807  * For details about the behaviour, see g_file_replace() which does the same
1808  * thing but returns an output stream only.
1809  *
1810  * Note that in many non-local file cases read and write streams are not
1811  * supported, so make sure you really need to do read and write streaming,
1812  * rather than just opening for reading or writing.
1813  *
1814  * Returns: (transfer full): a #GFileIOStream or %NULL on error.
1815  *     Free the returned object with g_object_unref().
1816  *
1817  * Since: 2.22
1818  */
1819 GFileIOStream *
1820 g_file_replace_readwrite (GFile             *file,
1821                           const char        *etag,
1822                           gboolean           make_backup,
1823                           GFileCreateFlags   flags,
1824                           GCancellable      *cancellable,
1825                           GError           **error)
1826 {
1827   GFileIface *iface;
1828
1829   g_return_val_if_fail (G_IS_FILE (file), NULL);
1830
1831   if (g_cancellable_set_error_if_cancelled (cancellable, error))
1832     return NULL;
1833
1834   iface = G_FILE_GET_IFACE (file);
1835
1836   if (iface->replace_readwrite == NULL)
1837     {
1838       g_set_error_literal (error, G_IO_ERROR,
1839                            G_IO_ERROR_NOT_SUPPORTED,
1840                            _("Operation not supported"));
1841       return NULL;
1842     }
1843
1844   return (* iface->replace_readwrite) (file, etag, make_backup, flags, cancellable, error);
1845 }
1846
1847 /**
1848  * g_file_read_async:
1849  * @file: input #GFile
1850  * @io_priority: the <link linkend="io-priority">I/O priority</link>
1851  *     of the request.
1852  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
1853  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied
1854  * @user_data: (closure): the data to pass to callback function
1855  *
1856  * Asynchronously opens @file for reading.
1857  *
1858  * For more details, see g_file_read() which is
1859  * the synchronous version of this call.
1860  *
1861  * When the operation is finished, @callback will be called. You can then call
1862  * g_file_read_finish() to get the result of the operation.
1863  **/
1864 void
1865 g_file_read_async (GFile               *file,
1866                    int                  io_priority,
1867                    GCancellable        *cancellable,
1868                    GAsyncReadyCallback  callback,
1869                    gpointer             user_data)
1870 {
1871   GFileIface *iface;
1872   
1873   g_return_if_fail (G_IS_FILE (file));
1874
1875   iface = G_FILE_GET_IFACE (file);
1876   (* iface->read_async) (file,
1877                          io_priority,
1878                          cancellable,
1879                          callback,
1880                          user_data);
1881 }
1882
1883 /**
1884  * g_file_read_finish:
1885  * @file: input #GFile.
1886  * @res: a #GAsyncResult. 
1887  * @error: a #GError, or %NULL
1888  *
1889  * Finishes an asynchronous file read operation started with 
1890  * g_file_read_async(). 
1891  *  
1892  * Returns: (transfer full): a #GFileInputStream or %NULL on error.
1893  *     Free the returned object with g_object_unref().
1894  **/
1895 GFileInputStream *
1896 g_file_read_finish (GFile         *file,
1897                     GAsyncResult  *res,
1898                     GError       **error)
1899 {
1900   GFileIface *iface;
1901   
1902   g_return_val_if_fail (G_IS_FILE (file), NULL);
1903   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), NULL);
1904
1905   if (G_IS_SIMPLE_ASYNC_RESULT (res))
1906     {
1907       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
1908       if (g_simple_async_result_propagate_error (simple, error))
1909         return NULL;
1910     }
1911   
1912   iface = G_FILE_GET_IFACE (file);
1913   return (* iface->read_finish) (file, res, error);
1914 }
1915
1916 /**
1917  * g_file_append_to_async:
1918  * @file: input #GFile.
1919  * @flags: a set of #GFileCreateFlags.
1920  * @io_priority: the <link linkend="io-priority">I/O priority</link> 
1921  *     of the request. 
1922  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
1923  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied
1924  * @user_data: (closure): the data to pass to callback function
1925  * 
1926  * Asynchronously opens @file for appending.
1927  *
1928  * For more details, see g_file_append_to() which is
1929  * the synchronous version of this call.
1930  *
1931  * When the operation is finished, @callback will be called. You can then call
1932  * g_file_append_to_finish() to get the result of the operation.
1933  **/
1934 void
1935 g_file_append_to_async (GFile               *file,
1936                         GFileCreateFlags     flags,
1937                         int                  io_priority,
1938                         GCancellable        *cancellable,
1939                         GAsyncReadyCallback  callback,
1940                         gpointer             user_data)
1941 {
1942   GFileIface *iface;
1943   
1944   g_return_if_fail (G_IS_FILE (file));
1945
1946   iface = G_FILE_GET_IFACE (file);
1947   (* iface->append_to_async) (file,
1948                               flags,
1949                               io_priority,
1950                               cancellable,
1951                               callback,
1952                               user_data);
1953 }
1954
1955 /**
1956  * g_file_append_to_finish:
1957  * @file: input #GFile.
1958  * @res: #GAsyncResult
1959  * @error: a #GError, or %NULL
1960  * 
1961  * Finishes an asynchronous file append operation started with 
1962  * g_file_append_to_async(). 
1963  * 
1964  * Returns: (transfer full): a valid #GFileOutputStream or %NULL on error.
1965  *     Free the returned object with g_object_unref().
1966  **/
1967 GFileOutputStream *
1968 g_file_append_to_finish (GFile         *file,
1969                          GAsyncResult  *res,
1970                          GError       **error)
1971 {
1972   GFileIface *iface;
1973   
1974   g_return_val_if_fail (G_IS_FILE (file), NULL);
1975   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), NULL);
1976
1977   if (G_IS_SIMPLE_ASYNC_RESULT (res))
1978     {
1979       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
1980       if (g_simple_async_result_propagate_error (simple, error))
1981         return NULL;
1982     }
1983   
1984   iface = G_FILE_GET_IFACE (file);
1985   return (* iface->append_to_finish) (file, res, error);
1986 }
1987
1988 /**
1989  * g_file_create_async:
1990  * @file: input #GFile.
1991  * @flags: a set of #GFileCreateFlags.
1992  * @io_priority: the <link linkend="io-priority">I/O priority</link> 
1993  *     of the request.
1994  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
1995  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied
1996  * @user_data: (closure): the data to pass to callback function
1997  * 
1998  * Asynchronously creates a new file and returns an output stream for writing to it.
1999  * The file must not already exist.
2000  *
2001  * For more details, see g_file_create() which is
2002  * the synchronous version of this call.
2003  *
2004  * When the operation is finished, @callback will be called. You can then call
2005  * g_file_create_finish() to get the result of the operation.
2006  **/
2007 void
2008 g_file_create_async (GFile               *file,
2009                      GFileCreateFlags     flags,
2010                      int                  io_priority,
2011                      GCancellable        *cancellable,
2012                      GAsyncReadyCallback  callback,
2013                      gpointer             user_data)
2014 {
2015   GFileIface *iface;
2016   
2017   g_return_if_fail (G_IS_FILE (file));
2018
2019   iface = G_FILE_GET_IFACE (file);
2020   (* iface->create_async) (file,
2021                            flags,
2022                            io_priority,
2023                            cancellable,
2024                            callback,
2025                            user_data);
2026 }
2027
2028 /**
2029  * g_file_create_finish:
2030  * @file: input #GFile.
2031  * @res: a #GAsyncResult. 
2032  * @error: a #GError, or %NULL
2033  * 
2034  * Finishes an asynchronous file create operation started with 
2035  * g_file_create_async(). 
2036  * 
2037  * Returns: (transfer full): a #GFileOutputStream or %NULL on error.
2038  *     Free the returned object with g_object_unref().
2039  **/
2040 GFileOutputStream *
2041 g_file_create_finish (GFile         *file,
2042                       GAsyncResult  *res,
2043                       GError       **error)
2044 {
2045   GFileIface *iface;
2046   
2047   g_return_val_if_fail (G_IS_FILE (file), NULL);
2048   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), NULL);
2049
2050   if (G_IS_SIMPLE_ASYNC_RESULT (res))
2051     {
2052       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
2053       if (g_simple_async_result_propagate_error (simple, error))
2054         return NULL;
2055     }
2056   
2057   iface = G_FILE_GET_IFACE (file);
2058   return (* iface->create_finish) (file, res, error);
2059 }
2060
2061 /**
2062  * g_file_replace_async:
2063  * @file: input #GFile.
2064  * @etag: (allow-none): an <link linkend="gfile-etag">entity tag</link> for the 
2065  *     current #GFile, or NULL to ignore.
2066  * @make_backup: %TRUE if a backup should be created.
2067  * @flags: a set of #GFileCreateFlags.
2068  * @io_priority: the <link linkend="io-priority">I/O priority</link> 
2069  *     of the request.
2070  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
2071  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied
2072  * @user_data: (closure): the data to pass to callback function
2073  *
2074  * Asynchronously overwrites the file, replacing the contents, possibly
2075  * creating a backup copy of the file first.
2076  *
2077  * For more details, see g_file_replace() which is
2078  * the synchronous version of this call.
2079  *
2080  * When the operation is finished, @callback will be called. You can then call
2081  * g_file_replace_finish() to get the result of the operation.
2082  **/
2083 void
2084 g_file_replace_async (GFile               *file,
2085                       const char          *etag,
2086                       gboolean             make_backup,
2087                       GFileCreateFlags     flags,
2088                       int                  io_priority,
2089                       GCancellable        *cancellable,
2090                       GAsyncReadyCallback  callback,
2091                       gpointer             user_data)
2092 {
2093   GFileIface *iface;
2094   
2095   g_return_if_fail (G_IS_FILE (file));
2096
2097   iface = G_FILE_GET_IFACE (file);
2098   (* iface->replace_async) (file,
2099                             etag,
2100                             make_backup,
2101                             flags,
2102                             io_priority,
2103                             cancellable,
2104                             callback,
2105                             user_data);
2106 }
2107
2108 /**
2109  * g_file_replace_finish:
2110  * @file: input #GFile.
2111  * @res: a #GAsyncResult. 
2112  * @error: a #GError, or %NULL
2113  * 
2114  * Finishes an asynchronous file replace operation started with 
2115  * g_file_replace_async(). 
2116  * 
2117  * Returns: (transfer full): a #GFileOutputStream, or %NULL on error.
2118  *     Free the returned object with g_object_unref().
2119  **/
2120 GFileOutputStream *
2121 g_file_replace_finish (GFile         *file,
2122                        GAsyncResult  *res,
2123                        GError       **error)
2124 {
2125   GFileIface *iface;
2126   
2127   g_return_val_if_fail (G_IS_FILE (file), NULL);
2128   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), NULL);
2129
2130   if (G_IS_SIMPLE_ASYNC_RESULT (res))
2131     {
2132       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
2133       if (g_simple_async_result_propagate_error (simple, error))
2134         return NULL;
2135     }
2136
2137   iface = G_FILE_GET_IFACE (file);
2138   return (* iface->replace_finish) (file, res, error);
2139 }
2140
2141
2142 /**
2143  * g_file_open_readwrite_async:
2144  * @file: input #GFile.
2145  * @io_priority: the <link linkend="io-priority">I/O priority</link>
2146  *     of the request.
2147  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
2148  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied
2149  * @user_data: (closure): the data to pass to callback function
2150  *
2151  * Asynchronously opens @file for reading and writing.
2152  *
2153  * For more details, see g_file_open_readwrite() which is
2154  * the synchronous version of this call.
2155  *
2156  * When the operation is finished, @callback will be called. You can then call
2157  * g_file_open_readwrite_finish() to get the result of the operation.
2158  *
2159  * Since: 2.22
2160  **/
2161 void
2162 g_file_open_readwrite_async (GFile                      *file,
2163                              int                         io_priority,
2164                              GCancellable               *cancellable,
2165                              GAsyncReadyCallback         callback,
2166                              gpointer                    user_data)
2167 {
2168   GFileIface *iface;
2169
2170   g_return_if_fail (G_IS_FILE (file));
2171
2172   iface = G_FILE_GET_IFACE (file);
2173   (* iface->open_readwrite_async) (file,
2174                                    io_priority,
2175                                    cancellable,
2176                                    callback,
2177                                    user_data);
2178 }
2179
2180 /**
2181  * g_file_open_readwrite_finish:
2182  * @file: input #GFile.
2183  * @res: a #GAsyncResult.
2184  * @error: a #GError, or %NULL
2185  *
2186  * Finishes an asynchronous file read operation started with
2187  * g_file_open_readwrite_async().
2188  *
2189  * Returns: (transfer full): a #GFileIOStream or %NULL on error.
2190  *     Free the returned object with g_object_unref().
2191  *
2192  * Since: 2.22
2193  **/
2194 GFileIOStream *
2195 g_file_open_readwrite_finish (GFile                      *file,
2196                               GAsyncResult               *res,
2197                               GError                    **error)
2198 {
2199   GFileIface *iface;
2200
2201   g_return_val_if_fail (G_IS_FILE (file), NULL);
2202   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), NULL);
2203
2204   if (G_IS_SIMPLE_ASYNC_RESULT (res))
2205     {
2206       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
2207       if (g_simple_async_result_propagate_error (simple, error))
2208         return NULL;
2209     }
2210
2211   iface = G_FILE_GET_IFACE (file);
2212   return (* iface->open_readwrite_finish) (file, res, error);
2213 }
2214
2215
2216 /**
2217  * g_file_create_readwrite_async:
2218  * @file: input #GFile
2219  * @flags: a set of #GFileCreateFlags
2220  * @io_priority: the <link linkend="io-priority">I/O priority</link>
2221  *     of the request
2222  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore
2223  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied
2224  * @user_data: (closure): the data to pass to callback function
2225  *
2226  * Asynchronously creates a new file and returns a stream for reading and
2227  * writing to it. The file must not already exist.
2228  *
2229  * For more details, see g_file_create_readwrite() which is
2230  * the synchronous version of this call.
2231  *
2232  * When the operation is finished, @callback will be called. You can then
2233  * call g_file_create_readwrite_finish() to get the result of the operation.
2234  *
2235  * Since: 2.22
2236  */
2237 void
2238 g_file_create_readwrite_async (GFile               *file,
2239                                GFileCreateFlags     flags,
2240                                int                  io_priority,
2241                                GCancellable        *cancellable,
2242                                GAsyncReadyCallback  callback,
2243                                gpointer             user_data)
2244 {
2245   GFileIface *iface;
2246
2247   g_return_if_fail (G_IS_FILE (file));
2248
2249   iface = G_FILE_GET_IFACE (file);
2250   (* iface->create_readwrite_async) (file,
2251                                      flags,
2252                                      io_priority,
2253                                      cancellable,
2254                                      callback,
2255                                      user_data);
2256 }
2257
2258 /**
2259  * g_file_create_readwrite_finish:
2260  * @file: input #GFile
2261  * @res: a #GAsyncResult
2262  * @error: a #GError, or %NULL
2263  *
2264  * Finishes an asynchronous file create operation started with
2265  * g_file_create_readwrite_async().
2266  *
2267  * Returns: (transfer full): a #GFileIOStream or %NULL on error.
2268  *     Free the returned object with g_object_unref().
2269  *
2270  * Since: 2.22
2271  **/
2272 GFileIOStream *
2273 g_file_create_readwrite_finish (GFile         *file,
2274                                 GAsyncResult  *res,
2275                                 GError       **error)
2276 {
2277   GFileIface *iface;
2278
2279   g_return_val_if_fail (G_IS_FILE (file), NULL);
2280   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), NULL);
2281
2282   if (G_IS_SIMPLE_ASYNC_RESULT (res))
2283     {
2284       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
2285       if (g_simple_async_result_propagate_error (simple, error))
2286         return NULL;
2287     }
2288
2289   iface = G_FILE_GET_IFACE (file);
2290   return (* iface->create_readwrite_finish) (file, res, error);
2291 }
2292
2293 /**
2294  * g_file_replace_readwrite_async:
2295  * @file: input #GFile.
2296  * @etag: (allow-none): an <link linkend="gfile-etag">entity tag</link> for the
2297  *     current #GFile, or NULL to ignore.
2298  * @make_backup: %TRUE if a backup should be created.
2299  * @flags: a set of #GFileCreateFlags.
2300  * @io_priority: the <link linkend="io-priority">I/O priority</link>
2301  *     of the request.
2302  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
2303  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied
2304  * @user_data: (closure): the data to pass to callback function
2305  *
2306  * Asynchronously overwrites the file in read-write mode, replacing the
2307  * contents, possibly creating a backup copy of the file first.
2308  *
2309  * For more details, see g_file_replace_readwrite() which is
2310  * the synchronous version of this call.
2311  *
2312  * When the operation is finished, @callback will be called. You can then
2313  * call g_file_replace_readwrite_finish() to get the result of the operation.
2314  *
2315  * Since: 2.22
2316  */
2317 void
2318 g_file_replace_readwrite_async (GFile               *file,
2319                                 const char          *etag,
2320                                 gboolean             make_backup,
2321                                 GFileCreateFlags     flags,
2322                                 int                  io_priority,
2323                                 GCancellable        *cancellable,
2324                                 GAsyncReadyCallback  callback,
2325                                 gpointer             user_data)
2326 {
2327   GFileIface *iface;
2328
2329   g_return_if_fail (G_IS_FILE (file));
2330
2331   iface = G_FILE_GET_IFACE (file);
2332   (* iface->replace_readwrite_async) (file,
2333                                       etag,
2334                                       make_backup,
2335                                       flags,
2336                                       io_priority,
2337                                       cancellable,
2338                                       callback,
2339                                       user_data);
2340 }
2341
2342 /**
2343  * g_file_replace_readwrite_finish:
2344  * @file: input #GFile.
2345  * @res: a #GAsyncResult.
2346  * @error: a #GError, or %NULL
2347  *
2348  * Finishes an asynchronous file replace operation started with
2349  * g_file_replace_readwrite_async().
2350  *
2351  * Returns: (transfer full): a #GFileIOStream, or %NULL on error.
2352  *     Free the returned object with g_object_unref().
2353  *
2354  * Since: 2.22
2355  */
2356 GFileIOStream *
2357 g_file_replace_readwrite_finish (GFile         *file,
2358                                  GAsyncResult  *res,
2359                                  GError       **error)
2360 {
2361   GFileIface *iface;
2362
2363   g_return_val_if_fail (G_IS_FILE (file), NULL);
2364   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), NULL);
2365
2366   if (G_IS_SIMPLE_ASYNC_RESULT (res))
2367     {
2368       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
2369       if (g_simple_async_result_propagate_error (simple, error))
2370         return NULL;
2371     }
2372
2373   iface = G_FILE_GET_IFACE (file);
2374   return (* iface->replace_readwrite_finish) (file, res, error);
2375 }
2376
2377 static gboolean
2378 copy_symlink (GFile           *destination,
2379               GFileCopyFlags   flags,
2380               GCancellable    *cancellable,
2381               const char      *target,
2382               GError         **error)
2383 {
2384   GError *my_error;
2385   gboolean tried_delete;
2386   GFileInfo *info;
2387   GFileType file_type;
2388
2389   tried_delete = FALSE;
2390
2391  retry:
2392   my_error = NULL;
2393   if (!g_file_make_symbolic_link (destination, target, cancellable, &my_error))
2394     {
2395       /* Maybe it already existed, and we want to overwrite? */
2396       if (!tried_delete && (flags & G_FILE_COPY_OVERWRITE) && 
2397           my_error->domain == G_IO_ERROR && my_error->code == G_IO_ERROR_EXISTS)
2398         {
2399           g_error_free (my_error);
2400
2401
2402           /* Don't overwrite if the destination is a directory */
2403           info = g_file_query_info (destination, G_FILE_ATTRIBUTE_STANDARD_TYPE,
2404                                     G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS,
2405                                     cancellable, &my_error);
2406           if (info != NULL)
2407             {
2408               file_type = g_file_info_get_file_type (info);
2409               g_object_unref (info);
2410               
2411               if (file_type == G_FILE_TYPE_DIRECTORY)
2412                 {
2413                   g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_IS_DIRECTORY,
2414                                        _("Can't copy over directory"));
2415                   return FALSE;
2416                 }
2417             }
2418           
2419           if (!g_file_delete (destination, cancellable, error))
2420             return FALSE;
2421           
2422           tried_delete = TRUE;
2423           goto retry;
2424         }
2425             /* Nah, fail */
2426       g_propagate_error (error, my_error);
2427       return FALSE;
2428     }
2429
2430   return TRUE;
2431 }
2432
2433 static GInputStream *
2434 open_source_for_copy (GFile           *source,
2435                       GFile           *destination,
2436                       GFileCopyFlags   flags,
2437                       GCancellable    *cancellable,
2438                       GError         **error)
2439 {
2440   GError *my_error;
2441   GInputStream *in;
2442   GFileInfo *info;
2443   GFileType file_type;
2444   
2445   my_error = NULL;
2446   in = (GInputStream *)g_file_read (source, cancellable, &my_error);
2447   if (in != NULL)
2448     return in;
2449
2450   /* There was an error opening the source, try to set a good error for it: */
2451
2452   if (my_error->domain == G_IO_ERROR && my_error->code == G_IO_ERROR_IS_DIRECTORY)
2453     {
2454       /* The source is a directory, don't fail with WOULD_RECURSE immediately, 
2455        * as that is less useful to the app. Better check for errors on the 
2456        * target instead. 
2457        */
2458       g_error_free (my_error);
2459       my_error = NULL;
2460       
2461       info = g_file_query_info (destination, G_FILE_ATTRIBUTE_STANDARD_TYPE,
2462                                 G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS,
2463                                 cancellable, &my_error);
2464       if (info != NULL &&
2465           g_file_info_has_attribute (info, G_FILE_ATTRIBUTE_STANDARD_TYPE))
2466         {
2467           file_type = g_file_info_get_file_type (info);
2468           g_object_unref (info);
2469           
2470           if (flags & G_FILE_COPY_OVERWRITE)
2471             {
2472               if (file_type == G_FILE_TYPE_DIRECTORY)
2473                 {
2474                   g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_WOULD_MERGE,
2475                                        _("Can't copy directory over directory"));
2476                   return NULL;
2477                 }
2478               /* continue to would_recurse error */
2479             }
2480           else
2481             {
2482               g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_EXISTS,
2483                                    _("Target file exists"));
2484               return NULL;
2485             }
2486         }
2487       else
2488         {
2489           /* Error getting info from target, return that error 
2490            * (except for NOT_FOUND, which is no error here) 
2491            */
2492           if (my_error != NULL && !g_error_matches (my_error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND))
2493             {
2494               g_propagate_error (error, my_error);
2495               return NULL;
2496             }
2497           g_clear_error (&my_error);
2498         }
2499       
2500       g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_WOULD_RECURSE,
2501                            _("Can't recursively copy directory"));
2502       return NULL;
2503     }
2504
2505   g_propagate_error (error, my_error);
2506   return NULL;
2507 }
2508
2509 static gboolean
2510 should_copy (GFileAttributeInfo *info, 
2511              gboolean            as_move,
2512              gboolean            skip_perms)
2513 {
2514   if (skip_perms && strcmp(info->name, "unix::mode") == 0)
2515         return FALSE;
2516
2517   if (as_move)
2518     return info->flags & G_FILE_ATTRIBUTE_INFO_COPY_WHEN_MOVED;
2519   return info->flags & G_FILE_ATTRIBUTE_INFO_COPY_WITH_FILE;
2520 }
2521
2522 static char *
2523 build_attribute_list_for_copy (GFileAttributeInfoList *attributes,
2524                                GFileAttributeInfoList *namespaces,
2525                                gboolean                as_move,
2526                                gboolean                skip_perms)
2527 {
2528   GString *s;
2529   gboolean first;
2530   int i;
2531   
2532   first = TRUE;
2533   s = g_string_new ("");
2534
2535   if (attributes)
2536     {
2537       for (i = 0; i < attributes->n_infos; i++)
2538         {
2539           if (should_copy (&attributes->infos[i], as_move, skip_perms))
2540             {
2541               if (first)
2542                 first = FALSE;
2543               else
2544                 g_string_append_c (s, ',');
2545                 
2546               g_string_append (s, attributes->infos[i].name);
2547             }
2548         }
2549     }
2550
2551   if (namespaces)
2552     {
2553       for (i = 0; i < namespaces->n_infos; i++)
2554         {
2555           if (should_copy (&namespaces->infos[i], as_move, FALSE))
2556             {
2557               if (first)
2558                 first = FALSE;
2559               else
2560                 g_string_append_c (s, ',');
2561                 
2562               g_string_append (s, namespaces->infos[i].name);
2563               g_string_append (s, "::*");
2564             }
2565         }
2566     }
2567
2568   return g_string_free (s, FALSE);
2569 }
2570
2571 /**
2572  * g_file_copy_attributes:
2573  * @source: a #GFile with attributes.
2574  * @destination: a #GFile to copy attributes to.
2575  * @flags: a set of #GFileCopyFlags.
2576  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
2577  * @error: a #GError, %NULL to ignore.
2578  *
2579  * Copies the file attributes from @source to @destination. 
2580  *
2581  * Normally only a subset of the file attributes are copied,
2582  * those that are copies in a normal file copy operation
2583  * (which for instance does not include e.g. owner). However
2584  * if #G_FILE_COPY_ALL_METADATA is specified in @flags, then
2585  * all the metadata that is possible to copy is copied. This
2586  * is useful when implementing move by copy + delete source.
2587  *
2588  * Returns: %TRUE if the attributes were copied successfully, %FALSE otherwise.
2589  **/
2590 gboolean
2591 g_file_copy_attributes (GFile           *source,
2592                         GFile           *destination,
2593                         GFileCopyFlags   flags,
2594                         GCancellable    *cancellable,
2595                         GError         **error)
2596 {
2597   GFileAttributeInfoList *attributes, *namespaces;
2598   char *attrs_to_read;
2599   gboolean res;
2600   GFileInfo *info;
2601   gboolean as_move;
2602   gboolean source_nofollow_symlinks;
2603   gboolean skip_perms;
2604
2605   as_move = flags & G_FILE_COPY_ALL_METADATA;
2606   source_nofollow_symlinks = flags & G_FILE_COPY_NOFOLLOW_SYMLINKS;
2607   skip_perms = (flags & G_FILE_COPY_TARGET_DEFAULT_PERMS) != 0;
2608
2609   /* Ignore errors here, if the target supports no attributes there is nothing to copy */
2610   attributes = g_file_query_settable_attributes (destination, cancellable, NULL);
2611   namespaces = g_file_query_writable_namespaces (destination, cancellable, NULL);
2612
2613   if (attributes == NULL && namespaces == NULL)
2614     return TRUE;
2615
2616   attrs_to_read = build_attribute_list_for_copy (attributes, namespaces, as_move, skip_perms);
2617
2618   /* Ignore errors here, if we can't read some info (e.g. if it doesn't exist)
2619    * we just don't copy it. 
2620    */
2621   info = g_file_query_info (source, attrs_to_read,
2622                             source_nofollow_symlinks ? G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS:0,
2623                             cancellable,
2624                             NULL);
2625
2626   g_free (attrs_to_read);
2627   
2628   res = TRUE;
2629   if  (info)
2630     {
2631       res = g_file_set_attributes_from_info (destination,
2632                                              info,
2633                          G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS,
2634                                              cancellable,
2635                                              error);
2636       g_object_unref (info);
2637     }
2638   
2639   g_file_attribute_info_list_unref (attributes);
2640   g_file_attribute_info_list_unref (namespaces);
2641   
2642   return res;
2643 }
2644
2645 static gboolean
2646 copy_stream_with_progress (GInputStream           *in,
2647                            GOutputStream          *out,
2648                            GFile                  *source,
2649                            GCancellable           *cancellable,
2650                            GFileProgressCallback   progress_callback,
2651                            gpointer                progress_callback_data,
2652                            GError                **error)
2653 {
2654   gssize n_read, n_written;
2655   goffset current_size;
2656   char buffer[1024*64], *p;
2657   gboolean res;
2658   goffset total_size;
2659   GFileInfo *info;
2660
2661   total_size = -1;
2662   /* avoid performance impact of querying total size when it's not needed */
2663   if (progress_callback)
2664     {
2665       info = g_file_input_stream_query_info (G_FILE_INPUT_STREAM (in),
2666                                              G_FILE_ATTRIBUTE_STANDARD_SIZE,
2667                                              cancellable, NULL);
2668       if (info)
2669         {
2670           if (g_file_info_has_attribute (info, G_FILE_ATTRIBUTE_STANDARD_SIZE))
2671             total_size = g_file_info_get_size (info);
2672           g_object_unref (info);
2673         }
2674
2675       if (total_size == -1)
2676         {
2677           info = g_file_query_info (source, 
2678                                     G_FILE_ATTRIBUTE_STANDARD_SIZE,
2679                                     G_FILE_QUERY_INFO_NONE,
2680                                     cancellable, NULL);
2681           if (info)
2682             {
2683               if (g_file_info_has_attribute (info, G_FILE_ATTRIBUTE_STANDARD_SIZE))
2684                 total_size = g_file_info_get_size (info);
2685               g_object_unref (info);
2686             }
2687         }
2688     }
2689
2690   if (total_size == -1)
2691     total_size = 0;
2692   
2693   current_size = 0;
2694   res = TRUE;
2695   while (TRUE)
2696     {
2697       n_read = g_input_stream_read (in, buffer, sizeof (buffer), cancellable, error);
2698       if (n_read == -1)
2699         {
2700           res = FALSE;
2701           break;
2702         }
2703         
2704       if (n_read == 0)
2705         break;
2706
2707       current_size += n_read;
2708
2709       p = buffer;
2710       while (n_read > 0)
2711         {
2712           n_written = g_output_stream_write (out, p, n_read, cancellable, error);
2713           if (n_written == -1)
2714             {
2715               res = FALSE;
2716               break;
2717             }
2718
2719           p += n_written;
2720           n_read -= n_written;
2721         }
2722
2723       if (!res)
2724         break;
2725
2726       if (progress_callback)
2727         progress_callback (current_size, total_size, progress_callback_data);
2728     }
2729
2730   /* Make sure we send full copied size */
2731   if (progress_callback)
2732     progress_callback (current_size, total_size, progress_callback_data);
2733
2734   return res;
2735 }
2736
2737 #ifdef HAVE_SPLICE
2738
2739 static gboolean
2740 do_splice (int     fd_in,
2741            loff_t *off_in,
2742            int     fd_out,
2743            loff_t *off_out,
2744            size_t  len,
2745            long   *bytes_transferd,
2746            GError **error)
2747 {
2748   long result;
2749
2750 retry:
2751   result = splice (fd_in, off_in, fd_out, off_out, len, SPLICE_F_MORE);
2752
2753   if (result == -1)
2754     {
2755       int errsv = errno;
2756
2757       if (errsv == EINTR)
2758         goto retry;
2759       else if (errsv == ENOSYS || errsv == EINVAL)
2760         g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
2761                              _("Splice not supported"));
2762       else
2763         g_set_error (error, G_IO_ERROR,
2764                      g_io_error_from_errno (errsv),
2765                      _("Error splicing file: %s"),
2766                      g_strerror (errsv));
2767
2768       return FALSE;
2769     }
2770
2771   *bytes_transferd = result;
2772   return TRUE;
2773 }
2774
2775 static gboolean
2776 splice_stream_with_progress (GInputStream           *in,
2777                              GOutputStream          *out,
2778                              GCancellable           *cancellable,
2779                              GFileProgressCallback   progress_callback,
2780                              gpointer                progress_callback_data,
2781                              GError                **error)
2782 {
2783   int buffer[2];
2784   gboolean res;
2785   goffset total_size;
2786   loff_t offset_in;
2787   loff_t offset_out;
2788   int fd_in, fd_out;
2789
2790   fd_in = g_file_descriptor_based_get_fd (G_FILE_DESCRIPTOR_BASED (in));
2791   fd_out = g_file_descriptor_based_get_fd (G_FILE_DESCRIPTOR_BASED (out));
2792
2793   if (pipe (buffer) != 0)
2794     {
2795       g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
2796                            "Pipe creation failed");
2797       return FALSE;
2798     }
2799
2800   total_size = -1;
2801   /* avoid performance impact of querying total size when it's not needed */
2802   if (progress_callback)
2803     {
2804       struct stat sbuf;
2805
2806       if (fstat (fd_in, &sbuf) == 0)
2807         total_size = sbuf.st_size;
2808     }
2809
2810   if (total_size == -1)
2811     total_size = 0;
2812
2813   offset_in = offset_out = 0;
2814   res = FALSE;
2815   while (TRUE)
2816     {
2817       long n_read;
2818       long n_written;
2819
2820       if (g_cancellable_set_error_if_cancelled (cancellable, error))
2821         break;
2822
2823       if (!do_splice (fd_in, &offset_in, buffer[1], NULL, 1024*64, &n_read, error))
2824         break;
2825
2826       if (n_read == 0)
2827         {
2828           res = TRUE;
2829           break;
2830         }
2831
2832       while (n_read > 0)
2833         {
2834           if (g_cancellable_set_error_if_cancelled (cancellable, error))
2835             goto out;
2836
2837           if (!do_splice (buffer[0], NULL, fd_out, &offset_out, n_read, &n_written, error))
2838             goto out;
2839
2840           n_read -= n_written;
2841         }
2842
2843       if (progress_callback)
2844         progress_callback (offset_in, total_size, progress_callback_data);
2845     }
2846
2847   /* Make sure we send full copied size */
2848   if (progress_callback)
2849     progress_callback (offset_in, total_size, progress_callback_data);
2850
2851  out:
2852   close (buffer[0]);
2853   close (buffer[1]);
2854
2855   return res;
2856 }
2857 #endif
2858
2859 static gboolean
2860 file_copy_fallback (GFile                  *source,
2861                     GFile                  *destination,
2862                     GFileCopyFlags          flags,
2863                     GCancellable           *cancellable,
2864                     GFileProgressCallback   progress_callback,
2865                     gpointer                progress_callback_data,
2866                     GError                **error)
2867 {
2868   GInputStream *in;
2869   GOutputStream *out;
2870   GFileInfo *info;
2871   const char *target;
2872   gboolean result;
2873 #ifdef HAVE_SPLICE
2874   gboolean fallback = TRUE;
2875 #endif
2876
2877   /* need to know the file type */
2878   info = g_file_query_info (source,
2879                             G_FILE_ATTRIBUTE_STANDARD_TYPE "," G_FILE_ATTRIBUTE_STANDARD_SYMLINK_TARGET,
2880                             G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS,
2881                             cancellable,
2882                             error);
2883
2884   if (info == NULL)
2885           return FALSE;
2886
2887   /* Maybe copy the symlink? */
2888   if ((flags & G_FILE_COPY_NOFOLLOW_SYMLINKS) &&
2889       g_file_info_get_file_type (info) == G_FILE_TYPE_SYMBOLIC_LINK)
2890     {
2891       target = g_file_info_get_symlink_target (info);
2892       if (target)
2893         {
2894           if (!copy_symlink (destination, flags, cancellable, target, error))
2895             {
2896               g_object_unref (info);
2897               return FALSE;
2898             }
2899           
2900           g_object_unref (info);
2901           goto copied_file;
2902         }
2903         /* ... else fall back on a regular file copy */
2904         g_object_unref (info);
2905     }
2906   /* Handle "special" files (pipes, device nodes, ...)? */
2907   else if (g_file_info_get_file_type (info) == G_FILE_TYPE_SPECIAL)
2908     {
2909       /* FIXME: could try to recreate device nodes and others? */
2910
2911       g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
2912                            _("Can't copy special file"));
2913       g_object_unref (info);
2914       return FALSE;
2915     }
2916   /* Everything else should just fall back on a regular copy. */
2917   else
2918     g_object_unref (info);
2919
2920   in = open_source_for_copy (source, destination, flags, cancellable, error);
2921   if (in == NULL)
2922     return FALSE;
2923   
2924   if (flags & G_FILE_COPY_OVERWRITE)
2925     {
2926       out = (GOutputStream *)g_file_replace (destination,
2927                                              NULL,
2928                                              flags & G_FILE_COPY_BACKUP,
2929                                              G_FILE_CREATE_REPLACE_DESTINATION,
2930                                              cancellable, error);
2931     }
2932   else
2933     {
2934       out = (GOutputStream *)g_file_create (destination, 0, cancellable, error);
2935     }
2936
2937   if (out == NULL)
2938     {
2939       g_object_unref (in);
2940       return FALSE;
2941     }
2942
2943 #ifdef HAVE_SPLICE
2944   if (G_IS_FILE_DESCRIPTOR_BASED (in) && G_IS_FILE_DESCRIPTOR_BASED (out))
2945     {
2946       GError *splice_err = NULL;
2947
2948       result = splice_stream_with_progress (in, out, cancellable,
2949                                             progress_callback, progress_callback_data,
2950                                             &splice_err);
2951
2952       if (result || !g_error_matches (splice_err, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED))
2953         {
2954           fallback = FALSE;
2955           if (!result)
2956             g_propagate_error (error, splice_err);
2957         }
2958       else
2959         g_clear_error (&splice_err);
2960     }
2961
2962   if (fallback)
2963 #endif
2964     result = copy_stream_with_progress (in, out, source, cancellable,
2965                                         progress_callback, progress_callback_data,
2966                                         error);
2967
2968   /* Don't care about errors in source here */
2969   g_input_stream_close (in, cancellable, NULL);
2970
2971   /* But write errors on close are bad! */
2972   if (!g_output_stream_close (out, cancellable, result ? error : NULL))
2973     result = FALSE;
2974
2975   g_object_unref (in);
2976   g_object_unref (out);
2977
2978   if (result == FALSE)
2979     return FALSE;
2980
2981  copied_file:
2982   /* Ignore errors here. Failure to copy metadata is not a hard error */
2983   g_file_copy_attributes (source, destination,
2984                           flags, cancellable, NULL);
2985   
2986   return TRUE;
2987 }
2988
2989 /**
2990  * g_file_copy:
2991  * @source: input #GFile.
2992  * @destination: destination #GFile
2993  * @flags: set of #GFileCopyFlags
2994  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore
2995  * @progress_callback: (allow-none) (scope call): function to callback with
2996  *     progress information, or %NULL if progress information is not needed
2997  * @progress_callback_data: (closure): user data to pass to @progress_callback
2998  * @error: #GError to set on error, or %NULL
2999  *
3000  * Copies the file @source to the location specified by @destination.
3001  * Can not handle recursive copies of directories.
3002  *
3003  * If the flag #G_FILE_COPY_OVERWRITE is specified an already
3004  * existing @destination file is overwritten.
3005  *
3006  * If the flag #G_FILE_COPY_NOFOLLOW_SYMLINKS is specified then symlinks
3007  * will be copied as symlinks, otherwise the target of the
3008  * @source symlink will be copied.
3009  *
3010  * If @cancellable is not %NULL, then the operation can be cancelled by
3011  * triggering the cancellable object from another thread. If the operation
3012  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
3013  *
3014  * If @progress_callback is not %NULL, then the operation can be monitored by
3015  * setting this to a #GFileProgressCallback function. @progress_callback_data
3016  * will be passed to this function. It is guaranteed that this callback will
3017  * be called after all data has been transferred with the total number of bytes
3018  * copied during the operation.
3019  *
3020  * If the @source file does not exist then the G_IO_ERROR_NOT_FOUND
3021  * error is returned, independent on the status of the @destination.
3022  *
3023  * If #G_FILE_COPY_OVERWRITE is not specified and the target exists, then the
3024  * error G_IO_ERROR_EXISTS is returned.
3025  *
3026  * If trying to overwrite a file over a directory the G_IO_ERROR_IS_DIRECTORY
3027  * error is returned. If trying to overwrite a directory with a directory the
3028  * G_IO_ERROR_WOULD_MERGE error is returned.
3029  *
3030  * If the source is a directory and the target does not exist, or
3031  * #G_FILE_COPY_OVERWRITE is specified and the target is a file, then the
3032  * G_IO_ERROR_WOULD_RECURSE error is returned.
3033  *
3034  * If you are interested in copying the #GFile object itself (not the on-disk
3035  * file), see g_file_dup().
3036  *
3037  * Returns: %TRUE on success, %FALSE otherwise.
3038  **/
3039 gboolean
3040 g_file_copy (GFile                  *source,
3041              GFile                  *destination,
3042              GFileCopyFlags          flags,
3043              GCancellable           *cancellable,
3044              GFileProgressCallback   progress_callback,
3045              gpointer                progress_callback_data,
3046              GError                **error)
3047 {
3048   GFileIface *iface;
3049   GError *my_error;
3050   gboolean res;
3051
3052   g_return_val_if_fail (G_IS_FILE (source), FALSE);
3053   g_return_val_if_fail (G_IS_FILE (destination), FALSE);
3054
3055   if (g_cancellable_set_error_if_cancelled (cancellable, error))
3056     return FALSE;
3057   
3058   iface = G_FILE_GET_IFACE (destination);
3059   if (iface->copy)
3060     {
3061       my_error = NULL;
3062       res = (* iface->copy) (source, destination,
3063                              flags, cancellable,
3064                              progress_callback, progress_callback_data,
3065                              &my_error);
3066       
3067       if (res)
3068         return TRUE;
3069       
3070       if (my_error->domain != G_IO_ERROR || my_error->code != G_IO_ERROR_NOT_SUPPORTED)
3071         {
3072           g_propagate_error (error, my_error);
3073               return FALSE;
3074         }
3075       else
3076         g_clear_error (&my_error);
3077     }
3078
3079   /* If the types are different, and the destination method failed
3080      also try the source method */
3081   if (G_OBJECT_TYPE (source) != G_OBJECT_TYPE (destination))
3082     {
3083       iface = G_FILE_GET_IFACE (source);
3084       
3085       if (iface->copy)
3086         {
3087           my_error = NULL;
3088           res = (* iface->copy) (source, destination,
3089                                  flags, cancellable,
3090                                  progress_callback, progress_callback_data,
3091                                  &my_error);
3092           
3093           if (res)
3094             return TRUE;
3095           
3096           if (my_error->domain != G_IO_ERROR || my_error->code != G_IO_ERROR_NOT_SUPPORTED)
3097             {
3098               g_propagate_error (error, my_error);
3099               return FALSE;
3100             }
3101           else
3102             g_clear_error (&my_error);
3103         }
3104     }
3105   
3106   return file_copy_fallback (source, destination, flags, cancellable,
3107                              progress_callback, progress_callback_data,
3108                              error);
3109 }
3110
3111 /**
3112  * g_file_copy_async: (skip)
3113  * @source: input #GFile.
3114  * @destination: destination #GFile
3115  * @flags: set of #GFileCopyFlags
3116  * @io_priority: the <link linkend="io-priority">I/O priority</link>
3117  *     of the request
3118  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore
3119  * @progress_callback: (allow-none): function to callback with progress
3120  *     information, or %NULL if progress information is not needed
3121  * @progress_callback_data: (closure): user data to pass to @progress_callback
3122  * @callback: a #GAsyncReadyCallback to call when the request is satisfied
3123  * @user_data: the data to pass to callback function
3124  *
3125  * Copies the file @source to the location specified by @destination
3126  * asynchronously. For details of the behaviour, see g_file_copy().
3127  *
3128  * If @progress_callback is not %NULL, then that function that will be called
3129  * just like in g_file_copy(), however the callback will run in the main loop,
3130  * not in the thread that is doing the I/O operation.
3131  *
3132  * When the operation is finished, @callback will be called. You can then call
3133  * g_file_copy_finish() to get the result of the operation.
3134  **/
3135 void
3136 g_file_copy_async (GFile                  *source,
3137                    GFile                  *destination,
3138                    GFileCopyFlags          flags,
3139                    int                     io_priority,
3140                    GCancellable           *cancellable,
3141                    GFileProgressCallback   progress_callback,
3142                    gpointer                progress_callback_data,
3143                    GAsyncReadyCallback     callback,
3144                    gpointer                user_data)
3145 {
3146   GFileIface *iface;
3147
3148   g_return_if_fail (G_IS_FILE (source));
3149   g_return_if_fail (G_IS_FILE (destination));
3150
3151   iface = G_FILE_GET_IFACE (source);
3152   (* iface->copy_async) (source,
3153                          destination,
3154                          flags,
3155                          io_priority,
3156                          cancellable,
3157                          progress_callback,
3158                          progress_callback_data,
3159                          callback,
3160                          user_data);
3161 }
3162
3163 /**
3164  * g_file_copy_finish:
3165  * @file: input #GFile.
3166  * @res: a #GAsyncResult. 
3167  * @error: a #GError, or %NULL
3168  * 
3169  * Finishes copying the file started with 
3170  * g_file_copy_async().
3171  * 
3172  * Returns: a %TRUE on success, %FALSE on error.
3173  **/
3174 gboolean
3175 g_file_copy_finish (GFile        *file,
3176                     GAsyncResult *res,
3177                     GError      **error)
3178 {
3179   GFileIface *iface;
3180   
3181   g_return_val_if_fail (G_IS_FILE (file), FALSE);
3182   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), FALSE);
3183
3184   if (G_IS_SIMPLE_ASYNC_RESULT (res))
3185     {
3186       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
3187       
3188       if (g_simple_async_result_propagate_error (simple, error))
3189         return FALSE;
3190     }
3191   
3192   iface = G_FILE_GET_IFACE (file);
3193   return (* iface->copy_finish) (file, res, error);
3194 }
3195
3196 /**
3197  * g_file_move:
3198  * @source: #GFile pointing to the source location.
3199  * @destination: #GFile pointing to the destination location.
3200  * @flags: set of #GFileCopyFlags.
3201  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3202  * @progress_callback: (scope call): #GFileProgressCallback function for updates.
3203  * @progress_callback_data: (closure): gpointer to user data for the callback function.
3204  * @error: #GError for returning error conditions, or %NULL
3205  *
3206  *
3207  * Tries to move the file or directory @source to the location specified by @destination.
3208  * If native move operations are supported then this is used, otherwise a copy + delete
3209  * fallback is used. The native implementation may support moving directories (for instance
3210  * on moves inside the same filesystem), but the fallback code does not.
3211  * 
3212  * If the flag #G_FILE_COPY_OVERWRITE is specified an already
3213  * existing @destination file is overwritten.
3214  *
3215  * If the flag #G_FILE_COPY_NOFOLLOW_SYMLINKS is specified then symlinks
3216  * will be copied as symlinks, otherwise the target of the
3217  * @source symlink will be copied.
3218  *
3219  * If @cancellable is not %NULL, then the operation can be cancelled by
3220  * triggering the cancellable object from another thread. If the operation
3221  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
3222  * 
3223  * If @progress_callback is not %NULL, then the operation can be monitored by
3224  * setting this to a #GFileProgressCallback function. @progress_callback_data
3225  * will be passed to this function. It is guaranteed that this callback will
3226  * be called after all data has been transferred with the total number of bytes
3227  * copied during the operation.
3228  * 
3229  * If the @source file does not exist then the G_IO_ERROR_NOT_FOUND
3230  * error is returned, independent on the status of the @destination.
3231  *
3232  * If #G_FILE_COPY_OVERWRITE is not specified and the target exists, then the
3233  * error G_IO_ERROR_EXISTS is returned.
3234  *
3235  * If trying to overwrite a file over a directory the G_IO_ERROR_IS_DIRECTORY
3236  * error is returned. If trying to overwrite a directory with a directory the
3237  * G_IO_ERROR_WOULD_MERGE error is returned.
3238  *
3239  * If the source is a directory and the target does not exist, or #G_FILE_COPY_OVERWRITE is
3240  * specified and the target is a file, then the G_IO_ERROR_WOULD_RECURSE error
3241  * may be returned (if the native move operation isn't available).
3242  *
3243  * Returns: %TRUE on successful move, %FALSE otherwise.
3244  **/
3245 gboolean
3246 g_file_move (GFile                  *source,
3247              GFile                  *destination,
3248              GFileCopyFlags          flags,
3249              GCancellable           *cancellable,
3250              GFileProgressCallback   progress_callback,
3251              gpointer                progress_callback_data,
3252              GError                **error)
3253 {
3254   GFileIface *iface;
3255   GError *my_error;
3256   gboolean res;
3257
3258   g_return_val_if_fail (G_IS_FILE (source), FALSE);
3259   g_return_val_if_fail (G_IS_FILE (destination), FALSE);
3260
3261   if (g_cancellable_set_error_if_cancelled (cancellable, error))
3262     return FALSE;
3263   
3264   iface = G_FILE_GET_IFACE (destination);
3265   if (iface->move)
3266     {
3267       my_error = NULL;
3268       res = (* iface->move) (source, destination,
3269                              flags, cancellable,
3270                              progress_callback, progress_callback_data,
3271                              &my_error);
3272       
3273       if (res)
3274         return TRUE;
3275       
3276       if (my_error->domain != G_IO_ERROR || my_error->code != G_IO_ERROR_NOT_SUPPORTED)
3277         {
3278           g_propagate_error (error, my_error);
3279           return FALSE;
3280         }
3281     }
3282
3283   /* If the types are different, and the destination method failed
3284      also try the source method */
3285   if (G_OBJECT_TYPE (source) != G_OBJECT_TYPE (destination))
3286     {
3287       iface = G_FILE_GET_IFACE (source);
3288       
3289       if (iface->move)
3290         {
3291           my_error = NULL;
3292           res = (* iface->move) (source, destination,
3293                                  flags, cancellable,
3294                                  progress_callback, progress_callback_data,
3295                                  &my_error);
3296           
3297           if (res)
3298             return TRUE;
3299           
3300           if (my_error->domain != G_IO_ERROR || my_error->code != G_IO_ERROR_NOT_SUPPORTED)
3301             {
3302               g_propagate_error (error, my_error);
3303               return FALSE;
3304             }
3305         }
3306     }
3307   
3308   if (flags & G_FILE_COPY_NO_FALLBACK_FOR_MOVE)
3309     {  
3310       g_set_error_literal (error, G_IO_ERROR,
3311                            G_IO_ERROR_NOT_SUPPORTED,
3312                            _("Operation not supported"));
3313       return FALSE;
3314     }
3315   
3316   flags |= G_FILE_COPY_ALL_METADATA;
3317   if (!g_file_copy (source, destination, flags, cancellable,
3318                     progress_callback, progress_callback_data,
3319                     error))
3320     return FALSE;
3321
3322   return g_file_delete (source, cancellable, error);
3323 }
3324
3325 /**
3326  * g_file_make_directory
3327  * @file: input #GFile.
3328  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3329  * @error: a #GError, or %NULL 
3330  *
3331  * Creates a directory. Note that this will only create a child directory of
3332  * the immediate parent directory of the path or URI given by the #GFile. To 
3333  * recursively create directories, see g_file_make_directory_with_parents().
3334  * This function will fail if the parent directory does not exist, setting 
3335  * @error to %G_IO_ERROR_NOT_FOUND. If the file system doesn't support creating
3336  * directories, this function will fail, setting @error to 
3337  * %G_IO_ERROR_NOT_SUPPORTED.
3338  *
3339  * For a local #GFile the newly created directory will have the default
3340  * (current) ownership and permissions of the current process.
3341  * 
3342  * If @cancellable is not %NULL, then the operation can be cancelled by
3343  * triggering the cancellable object from another thread. If the operation
3344  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
3345  * 
3346  * Returns: %TRUE on successful creation, %FALSE otherwise.
3347  **/
3348 gboolean
3349 g_file_make_directory (GFile         *file,
3350                        GCancellable  *cancellable,
3351                        GError       **error)
3352 {
3353   GFileIface *iface;
3354
3355   g_return_val_if_fail (G_IS_FILE (file), FALSE);
3356
3357   if (g_cancellable_set_error_if_cancelled (cancellable, error))
3358     return FALSE;
3359   
3360   iface = G_FILE_GET_IFACE (file);
3361
3362   if (iface->make_directory == NULL)
3363     {
3364       g_set_error_literal (error, G_IO_ERROR,
3365                            G_IO_ERROR_NOT_SUPPORTED,
3366                            _("Operation not supported"));
3367       return FALSE;
3368     }
3369   
3370   return (* iface->make_directory) (file, cancellable, error);
3371 }
3372
3373 /**
3374  * g_file_make_directory_with_parents:
3375  * @file: input #GFile.
3376  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3377  * @error: a #GError, or %NULL 
3378  *
3379  * Creates a directory and any parent directories that may not exist similar to
3380  * 'mkdir -p'. If the file system does not support creating directories, this
3381  * function will fail, setting @error to %G_IO_ERROR_NOT_SUPPORTED. If the
3382  * directory itself already exists, this function will fail setting @error
3383  * to %G_IO_ERROR_EXISTS, unlike the similar g_mkdir_with_parents().
3384  * 
3385  * For a local #GFile the newly created directories will have the default
3386  * (current) ownership and permissions of the current process.
3387  * 
3388  * If @cancellable is not %NULL, then the operation can be cancelled by
3389  * triggering the cancellable object from another thread. If the operation
3390  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
3391  * 
3392  * Returns: %TRUE if all directories have been successfully created, %FALSE
3393  * otherwise.
3394  *
3395  * Since: 2.18
3396  **/
3397 gboolean
3398 g_file_make_directory_with_parents (GFile         *file,
3399                                     GCancellable  *cancellable,
3400                                     GError       **error)
3401 {
3402   gboolean result;
3403   GFile *parent_file, *work_file;
3404   GList *list = NULL, *l;
3405   GError *my_error = NULL;
3406
3407   if (g_cancellable_set_error_if_cancelled (cancellable, error))
3408     return FALSE;
3409   
3410   result = g_file_make_directory (file, cancellable, &my_error);
3411   if (result || my_error->code != G_IO_ERROR_NOT_FOUND) 
3412     {
3413       if (my_error)
3414         g_propagate_error (error, my_error);
3415       return result;
3416     }
3417   
3418   work_file = file;
3419   
3420   while (!result && my_error->code == G_IO_ERROR_NOT_FOUND) 
3421     {
3422       g_clear_error (&my_error);
3423     
3424       parent_file = g_file_get_parent (work_file);
3425       if (parent_file == NULL)
3426         break;
3427       result = g_file_make_directory (parent_file, cancellable, &my_error);
3428     
3429       if (!result && my_error->code == G_IO_ERROR_NOT_FOUND)
3430         list = g_list_prepend (list, parent_file);
3431
3432       work_file = parent_file;
3433     }
3434
3435   for (l = list; result && l; l = l->next)
3436     {
3437       result = g_file_make_directory ((GFile *) l->data, cancellable, &my_error);
3438     }
3439   
3440   /* Clean up */
3441   while (list != NULL) 
3442     {
3443       g_object_unref ((GFile *) list->data);
3444       list = g_list_remove (list, list->data);
3445     }
3446
3447   if (!result) 
3448     {
3449       g_propagate_error (error, my_error);
3450       return result;
3451     }
3452   
3453   return g_file_make_directory (file, cancellable, error);
3454 }
3455
3456 /**
3457  * g_file_make_symbolic_link:
3458  * @file: a #GFile with the name of the symlink to create
3459  * @symlink_value: a string with the path for the target of the new symlink
3460  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3461  * @error: a #GError.
3462  *
3463  * Creates a symbolic link named @file which contains the string
3464  * @symlink_value.
3465  *
3466  * If @cancellable is not %NULL, then the operation can be cancelled by
3467  * triggering the cancellable object from another thread. If the operation
3468  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
3469  *
3470  * Returns: %TRUE on the creation of a new symlink, %FALSE otherwise.
3471  */
3472 gboolean
3473 g_file_make_symbolic_link (GFile         *file,
3474                            const char    *symlink_value,
3475                            GCancellable  *cancellable,
3476                            GError       **error)
3477 {
3478   GFileIface *iface;
3479
3480   g_return_val_if_fail (G_IS_FILE (file), FALSE);
3481   g_return_val_if_fail (symlink_value != NULL, FALSE);
3482
3483   if (g_cancellable_set_error_if_cancelled (cancellable, error))
3484     return FALSE;
3485
3486   if (*symlink_value == '\0')
3487     {
3488       g_set_error_literal (error, G_IO_ERROR,
3489                            G_IO_ERROR_INVALID_ARGUMENT,
3490                            _("Invalid symlink value given"));
3491       return FALSE;
3492     }
3493   
3494   iface = G_FILE_GET_IFACE (file);
3495
3496   if (iface->make_symbolic_link == NULL)
3497     {
3498       g_set_error_literal (error, G_IO_ERROR,
3499                            G_IO_ERROR_NOT_SUPPORTED,
3500                            _("Operation not supported"));
3501       return FALSE;
3502     }
3503   
3504   return (* iface->make_symbolic_link) (file, symlink_value, cancellable, error);
3505 }
3506
3507 /**
3508  * g_file_delete:
3509  * @file: input #GFile.
3510  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3511  * @error: a #GError, or %NULL 
3512  * 
3513  * Deletes a file. If the @file is a directory, it will only be deleted if it 
3514  * is empty.
3515  * 
3516  * If @cancellable is not %NULL, then the operation can be cancelled by
3517  * triggering the cancellable object from another thread. If the operation
3518  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
3519  *
3520  * Virtual: delete_file
3521  * Returns: %TRUE if the file was deleted. %FALSE otherwise.
3522  **/
3523 gboolean
3524 g_file_delete (GFile         *file,
3525                GCancellable  *cancellable,
3526                GError       **error)
3527 {
3528   GFileIface *iface;
3529   
3530   g_return_val_if_fail (G_IS_FILE (file), FALSE);
3531
3532   if (g_cancellable_set_error_if_cancelled (cancellable, error))
3533     return FALSE;
3534   
3535   iface = G_FILE_GET_IFACE (file);
3536
3537   if (iface->delete_file == NULL)
3538     {
3539       g_set_error_literal (error, G_IO_ERROR,
3540                            G_IO_ERROR_NOT_SUPPORTED,
3541                            _("Operation not supported"));
3542       return FALSE;
3543     }
3544   
3545   return (* iface->delete_file) (file, cancellable, error);
3546 }
3547
3548 /**
3549  * g_file_trash:
3550  * @file: #GFile to send to trash.
3551  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3552  * @error: a #GError, or %NULL
3553  *
3554  * Sends @file to the "Trashcan", if possible. This is similar to
3555  * deleting it, but the user can recover it before emptying the trashcan.
3556  * Not all file systems support trashing, so this call can return the
3557  * %G_IO_ERROR_NOT_SUPPORTED error.
3558  *
3559  *
3560  * If @cancellable is not %NULL, then the operation can be cancelled by
3561  * triggering the cancellable object from another thread. If the operation
3562  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
3563  * 
3564  * Returns: %TRUE on successful trash, %FALSE otherwise.
3565  **/
3566 gboolean
3567 g_file_trash (GFile         *file,
3568               GCancellable  *cancellable,
3569               GError       **error)
3570 {
3571   GFileIface *iface;
3572   
3573   g_return_val_if_fail (G_IS_FILE (file), FALSE);
3574
3575   if (g_cancellable_set_error_if_cancelled (cancellable, error))
3576     return FALSE;
3577   
3578   iface = G_FILE_GET_IFACE (file);
3579
3580   if (iface->trash == NULL)
3581     {
3582       g_set_error_literal (error,
3583                            G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
3584                            _("Trash not supported"));
3585       return FALSE;
3586     }
3587   
3588   return (* iface->trash) (file, cancellable, error);
3589 }
3590
3591 /**
3592  * g_file_set_display_name:
3593  * @file: input #GFile.
3594  * @display_name: a string.
3595  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3596  * @error: a #GError, or %NULL
3597  * 
3598  * Renames @file to the specified display name.
3599  *
3600  * The display name is converted from UTF8 to the correct encoding for the target
3601  * filesystem if possible and the @file is renamed to this.
3602  * 
3603  * If you want to implement a rename operation in the user interface the edit name
3604  * (#G_FILE_ATTRIBUTE_STANDARD_EDIT_NAME) should be used as the initial value in the rename
3605  * widget, and then the result after editing should be passed to g_file_set_display_name().
3606  *
3607  * On success the resulting converted filename is returned.
3608  * 
3609  * If @cancellable is not %NULL, then the operation can be cancelled by
3610  * triggering the cancellable object from another thread. If the operation
3611  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
3612  * 
3613  * Returns: (transfer full): a #GFile specifying what @file was renamed to, or %NULL 
3614  *     if there was an error.
3615  *     Free the returned object with g_object_unref().
3616  **/
3617 GFile *
3618 g_file_set_display_name (GFile         *file,
3619                          const char    *display_name,
3620                          GCancellable  *cancellable,
3621                          GError       **error)
3622 {
3623   GFileIface *iface;
3624   
3625   g_return_val_if_fail (G_IS_FILE (file), NULL);
3626   g_return_val_if_fail (display_name != NULL, NULL);
3627
3628   if (strchr (display_name, G_DIR_SEPARATOR) != NULL)
3629     {
3630       g_set_error (error,
3631                    G_IO_ERROR,
3632                    G_IO_ERROR_INVALID_ARGUMENT,
3633                    _("File names cannot contain '%c'"), G_DIR_SEPARATOR);
3634       return NULL;
3635     }
3636   
3637   if (g_cancellable_set_error_if_cancelled (cancellable, error))
3638     return NULL;
3639   
3640   iface = G_FILE_GET_IFACE (file);
3641
3642   return (* iface->set_display_name) (file, display_name, cancellable, error);
3643 }
3644
3645 /**
3646  * g_file_set_display_name_async:
3647  * @file: input #GFile.
3648  * @display_name: a string.
3649  * @io_priority: the <link linkend="io-priority">I/O priority</link> 
3650  *     of the request. 
3651  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3652  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied
3653  * @user_data: (closure): the data to pass to callback function
3654  * 
3655  * Asynchronously sets the display name for a given #GFile.
3656  * 
3657  * For more details, see g_file_set_display_name() which is
3658  * the synchronous version of this call.
3659  *
3660  * When the operation is finished, @callback will be called. You can then call
3661  * g_file_set_display_name_finish() to get the result of the operation.
3662  **/
3663 void
3664 g_file_set_display_name_async (GFile               *file,
3665                                const char          *display_name,
3666                                int                  io_priority,
3667                                GCancellable        *cancellable,
3668                                GAsyncReadyCallback  callback,
3669                                gpointer             user_data)
3670 {
3671   GFileIface *iface;
3672   
3673   g_return_if_fail (G_IS_FILE (file));
3674   g_return_if_fail (display_name != NULL);
3675
3676   iface = G_FILE_GET_IFACE (file);
3677   (* iface->set_display_name_async) (file,
3678                                      display_name,
3679                                      io_priority,
3680                                      cancellable,
3681                                      callback,
3682                                      user_data);
3683 }
3684
3685 /**
3686  * g_file_set_display_name_finish:
3687  * @file: input #GFile.
3688  * @res: a #GAsyncResult. 
3689  * @error: a #GError, or %NULL
3690  * 
3691  * Finishes setting a display name started with 
3692  * g_file_set_display_name_async().
3693  * 
3694  * Returns: (transfer full): a #GFile or %NULL on error.
3695  *     Free the returned object with g_object_unref().
3696  **/
3697 GFile *
3698 g_file_set_display_name_finish (GFile         *file,
3699                                 GAsyncResult  *res,
3700                                 GError       **error)
3701 {
3702   GFileIface *iface;
3703   
3704   g_return_val_if_fail (G_IS_FILE (file), NULL);
3705   g_return_val_if_fail (G_IS_ASYNC_RESULT (res), NULL);
3706
3707   if (G_IS_SIMPLE_ASYNC_RESULT (res))
3708     {
3709       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
3710       if (g_simple_async_result_propagate_error (simple, error))
3711         return NULL;
3712     }
3713   
3714   iface = G_FILE_GET_IFACE (file);
3715   return (* iface->set_display_name_finish) (file, res, error);
3716 }
3717
3718 /**
3719  * g_file_query_settable_attributes:
3720  * @file: input #GFile.
3721  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3722  * @error: a #GError, or %NULL
3723  * 
3724  * Obtain the list of settable attributes for the file.
3725  *
3726  * Returns the type and full attribute name of all the attributes 
3727  * that can be set on this file. This doesn't mean setting it will always 
3728  * succeed though, you might get an access failure, or some specific 
3729  * file may not support a specific attribute.
3730  *
3731  * If @cancellable is not %NULL, then the operation can be cancelled by
3732  * triggering the cancellable object from another thread. If the operation
3733  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
3734  * 
3735  * Returns: a #GFileAttributeInfoList describing the settable attributes.
3736  * When you are done with it, release it with g_file_attribute_info_list_unref()
3737  **/
3738 GFileAttributeInfoList *
3739 g_file_query_settable_attributes (GFile         *file,
3740                                   GCancellable  *cancellable,
3741                                   GError       **error)
3742 {
3743   GFileIface *iface;
3744   GError *my_error;
3745   GFileAttributeInfoList *list;
3746
3747   g_return_val_if_fail (G_IS_FILE (file), NULL);
3748
3749   if (g_cancellable_set_error_if_cancelled (cancellable, error))
3750     return NULL;
3751   
3752   iface = G_FILE_GET_IFACE (file);
3753
3754   if (iface->query_settable_attributes == NULL)
3755     return g_file_attribute_info_list_new ();
3756
3757   my_error = NULL;
3758   list = (* iface->query_settable_attributes) (file, cancellable, &my_error);
3759   
3760   if (list == NULL)
3761     {
3762       if (my_error->domain == G_IO_ERROR && my_error->code == G_IO_ERROR_NOT_SUPPORTED)
3763         {
3764           list = g_file_attribute_info_list_new ();
3765           g_error_free (my_error);
3766         }
3767       else
3768         g_propagate_error (error, my_error);
3769     }
3770   
3771   return list;
3772 }
3773
3774 /**
3775  * g_file_query_writable_namespaces:
3776  * @file: input #GFile.
3777  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3778  * @error: a #GError, or %NULL
3779  * 
3780  * Obtain the list of attribute namespaces where new attributes 
3781  * can be created by a user. An example of this is extended
3782  * attributes (in the "xattr" namespace).
3783  *
3784  * If @cancellable is not %NULL, then the operation can be cancelled by
3785  * triggering the cancellable object from another thread. If the operation
3786  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
3787  * 
3788  * Returns: a #GFileAttributeInfoList describing the writable namespaces.
3789  * When you are done with it, release it with g_file_attribute_info_list_unref()
3790  **/
3791 GFileAttributeInfoList *
3792 g_file_query_writable_namespaces (GFile         *file,
3793                                   GCancellable  *cancellable,
3794                                   GError       **error)
3795 {
3796   GFileIface *iface;
3797   GError *my_error;
3798   GFileAttributeInfoList *list;
3799   
3800   g_return_val_if_fail (G_IS_FILE (file), NULL);
3801
3802   if (g_cancellable_set_error_if_cancelled (cancellable, error))
3803     return NULL;
3804   
3805   iface = G_FILE_GET_IFACE (file);
3806
3807   if (iface->query_writable_namespaces == NULL)
3808     return g_file_attribute_info_list_new ();
3809
3810   my_error = NULL;
3811   list = (* iface->query_writable_namespaces) (file, cancellable, &my_error);
3812   
3813   if (list == NULL)
3814     {
3815       if (my_error->domain == G_IO_ERROR && my_error->code == G_IO_ERROR_NOT_SUPPORTED)
3816         {
3817           list = g_file_attribute_info_list_new ();
3818           g_error_free (my_error);
3819         }
3820       else
3821         g_propagate_error (error, my_error);
3822     }
3823   
3824   return list;
3825 }
3826
3827 /**
3828  * g_file_set_attribute:
3829  * @file: input #GFile.
3830  * @attribute: a string containing the attribute's name.
3831  * @type: The type of the attribute
3832  * @value_p: (allow-none): a pointer to the value (or the pointer itself if the type is a pointer type)
3833  * @flags: a set of #GFileQueryInfoFlags.
3834  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3835  * @error: a #GError, or %NULL
3836  * 
3837  * Sets an attribute in the file with attribute name @attribute to @value.
3838  *
3839  * Some attributes can be unset by setting @attribute to
3840  * %G_FILE_ATTRIBUTE_TYPE_INVALID and @value_p to %NULL.
3841  * 
3842  * If @cancellable is not %NULL, then the operation can be cancelled by
3843  * triggering the cancellable object from another thread. If the operation
3844  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
3845  * 
3846  * Returns: %TRUE if the attribute was set, %FALSE otherwise.
3847  **/
3848 gboolean
3849 g_file_set_attribute (GFile                      *file,
3850                       const char                 *attribute,
3851                       GFileAttributeType          type,
3852                       gpointer                    value_p,
3853                       GFileQueryInfoFlags         flags,
3854                       GCancellable               *cancellable,
3855                       GError                    **error)
3856 {
3857   GFileIface *iface;
3858   
3859   g_return_val_if_fail (G_IS_FILE (file), FALSE);
3860   g_return_val_if_fail (attribute != NULL && *attribute != '\0', FALSE);
3861
3862   if (g_cancellable_set_error_if_cancelled (cancellable, error))
3863     return FALSE;
3864   
3865   iface = G_FILE_GET_IFACE (file);
3866
3867   if (iface->set_attribute == NULL)
3868     {
3869       g_set_error_literal (error, G_IO_ERROR,
3870                            G_IO_ERROR_NOT_SUPPORTED,
3871                            _("Operation not supported"));
3872       return FALSE;
3873     }
3874
3875   return (* iface->set_attribute) (file, attribute, type, value_p, flags, cancellable, error);
3876 }
3877
3878 /**
3879  * g_file_set_attributes_from_info:
3880  * @file: input #GFile.
3881  * @info: a #GFileInfo.
3882  * @flags: #GFileQueryInfoFlags
3883  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3884  * @error: a #GError, or %NULL 
3885  * 
3886  * Tries to set all attributes in the #GFileInfo on the target values, 
3887  * not stopping on the first error.
3888  * 
3889  * If there is any error during this operation then @error will be set to
3890  * the first error. Error on particular fields are flagged by setting 
3891  * the "status" field in the attribute value to 
3892  * %G_FILE_ATTRIBUTE_STATUS_ERROR_SETTING, which means you can also detect
3893  * further errors.
3894  *
3895  * If @cancellable is not %NULL, then the operation can be cancelled by
3896  * triggering the cancellable object from another thread. If the operation
3897  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
3898  * 
3899  * Returns: %TRUE if there was any error, %FALSE otherwise.
3900  **/
3901 gboolean
3902 g_file_set_attributes_from_info (GFile                *file,
3903                                  GFileInfo            *info,
3904                                  GFileQueryInfoFlags   flags,
3905                                  GCancellable         *cancellable,
3906                                  GError              **error)
3907 {
3908   GFileIface *iface;
3909
3910   g_return_val_if_fail (G_IS_FILE (file), FALSE);
3911   g_return_val_if_fail (G_IS_FILE_INFO (info), FALSE);
3912
3913   if (g_cancellable_set_error_if_cancelled (cancellable, error))
3914     return FALSE;
3915   
3916   g_file_info_clear_status (info);
3917   
3918   iface = G_FILE_GET_IFACE (file);
3919
3920   return (* iface->set_attributes_from_info) (file, 
3921                                               info, 
3922                                               flags, 
3923                                               cancellable, 
3924                                               error);
3925 }
3926
3927
3928 static gboolean
3929 g_file_real_set_attributes_from_info (GFile                *file,
3930                                       GFileInfo            *info,
3931                                       GFileQueryInfoFlags   flags,
3932                                       GCancellable         *cancellable,
3933                                       GError              **error)
3934 {
3935   char **attributes;
3936   int i;
3937   gboolean res;
3938   GFileAttributeValue *value;
3939   
3940   res = TRUE;
3941   
3942   attributes = g_file_info_list_attributes (info, NULL);
3943
3944   for (i = 0; attributes[i] != NULL; i++)
3945     {
3946       value = _g_file_info_get_attribute_value (info, attributes[i]);
3947
3948       if (value->status != G_FILE_ATTRIBUTE_STATUS_UNSET)
3949         continue;
3950
3951       if (!g_file_set_attribute (file, attributes[i],
3952                                  value->type, _g_file_attribute_value_peek_as_pointer (value),
3953                                  flags, cancellable, error))
3954         {
3955           value->status = G_FILE_ATTRIBUTE_STATUS_ERROR_SETTING;
3956           res = FALSE;
3957           /* Don't set error multiple times */
3958           error = NULL;
3959         }
3960       else
3961         value->status = G_FILE_ATTRIBUTE_STATUS_SET;
3962     }
3963   
3964   g_strfreev (attributes);
3965   
3966   return res;
3967 }
3968
3969 /**
3970  * g_file_set_attributes_async:
3971  * @file: input #GFile.
3972  * @info: a #GFileInfo.
3973  * @flags: a #GFileQueryInfoFlags.
3974  * @io_priority: the <link linkend="io-priority">I/O priority</link> 
3975  *     of the request. 
3976  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
3977  * @callback: (scope async): a #GAsyncReadyCallback. 
3978  * @user_data: (closure): a #gpointer.
3979  *
3980  * Asynchronously sets the attributes of @file with @info.
3981  * 
3982  * For more details, see g_file_set_attributes_from_info() which is
3983  * the synchronous version of this call.
3984  *
3985  * When the operation is finished, @callback will be called. You can then call
3986  * g_file_set_attributes_finish() to get the result of the operation.
3987  **/
3988 void
3989 g_file_set_attributes_async (GFile               *file,
3990                              GFileInfo           *info,
3991                              GFileQueryInfoFlags  flags,
3992                              int                  io_priority,
3993                              GCancellable        *cancellable,
3994                              GAsyncReadyCallback  callback,
3995                              gpointer             user_data)
3996 {
3997   GFileIface *iface;
3998   
3999   g_return_if_fail (G_IS_FILE (file));
4000   g_return_if_fail (G_IS_FILE_INFO (info));
4001
4002   iface = G_FILE_GET_IFACE (file);
4003   (* iface->set_attributes_async) (file, 
4004                                    info, 
4005                                    flags, 
4006                                    io_priority, 
4007                                    cancellable, 
4008                                    callback, 
4009                                    user_data);
4010 }
4011
4012 /**
4013  * g_file_set_attributes_finish:
4014  * @file: input #GFile.
4015  * @result: a #GAsyncResult.
4016  * @info: (out) (transfer full): a #GFileInfo.
4017  * @error: a #GError, or %NULL
4018  * 
4019  * Finishes setting an attribute started in g_file_set_attributes_async().
4020  * 
4021  * Returns: %TRUE if the attributes were set correctly, %FALSE otherwise.
4022  **/
4023 gboolean
4024 g_file_set_attributes_finish (GFile         *file,
4025                               GAsyncResult  *result,
4026                               GFileInfo    **info,
4027                               GError       **error)
4028 {
4029   GFileIface *iface;
4030   
4031   g_return_val_if_fail (G_IS_FILE (file), FALSE);
4032   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), FALSE);
4033
4034   /* No standard handling of errors here, as we must set info even
4035    * on errors 
4036    */
4037   iface = G_FILE_GET_IFACE (file);
4038   return (* iface->set_attributes_finish) (file, result, info, error);
4039 }
4040
4041 /**
4042  * g_file_set_attribute_string:
4043  * @file: input #GFile.
4044  * @attribute: a string containing the attribute's name.
4045  * @value: a string containing the attribute's value.
4046  * @flags: #GFileQueryInfoFlags.
4047  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4048  * @error: a #GError, or %NULL
4049  * 
4050  * Sets @attribute of type %G_FILE_ATTRIBUTE_TYPE_STRING to @value. 
4051  * If @attribute is of a different type, this operation will fail.
4052  * 
4053  * If @cancellable is not %NULL, then the operation can be cancelled by
4054  * triggering the cancellable object from another thread. If the operation
4055  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
4056  * 
4057  * Returns: %TRUE if the @attribute was successfully set, %FALSE otherwise.
4058  **/
4059 gboolean
4060 g_file_set_attribute_string (GFile                *file,
4061                              const char           *attribute,
4062                              const char           *value,
4063                              GFileQueryInfoFlags   flags,
4064                              GCancellable         *cancellable,
4065                              GError              **error)
4066 {
4067   return g_file_set_attribute (file, attribute,
4068                                G_FILE_ATTRIBUTE_TYPE_STRING, (gpointer)value,
4069                                flags, cancellable, error);
4070 }
4071
4072 /**
4073  * g_file_set_attribute_byte_string:
4074  * @file: input #GFile.
4075  * @attribute: a string containing the attribute's name.
4076  * @value: a string containing the attribute's new value.
4077  * @flags: a #GFileQueryInfoFlags.
4078  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4079  * @error: a #GError, or %NULL
4080  * 
4081  * Sets @attribute of type %G_FILE_ATTRIBUTE_TYPE_BYTE_STRING to @value. 
4082  * If @attribute is of a different type, this operation will fail, 
4083  * returning %FALSE. 
4084  * 
4085  * If @cancellable is not %NULL, then the operation can be cancelled by
4086  * triggering the cancellable object from another thread. If the operation
4087  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
4088  * 
4089  * Returns: %TRUE if the @attribute was successfully set to @value 
4090  * in the @file, %FALSE otherwise.
4091  **/
4092 gboolean
4093 g_file_set_attribute_byte_string  (GFile                *file,
4094                                    const char           *attribute,
4095                                    const char           *value,
4096                                    GFileQueryInfoFlags   flags,
4097                                    GCancellable         *cancellable,
4098                                    GError              **error)
4099 {
4100   return g_file_set_attribute (file, attribute,
4101                                G_FILE_ATTRIBUTE_TYPE_BYTE_STRING, (gpointer)value,
4102                                flags, cancellable, error);
4103 }
4104
4105 /**
4106  * g_file_set_attribute_uint32:
4107  * @file: input #GFile.
4108  * @attribute: a string containing the attribute's name.
4109  * @value: a #guint32 containing the attribute's new value.
4110  * @flags: a #GFileQueryInfoFlags.
4111  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4112  * @error: a #GError, or %NULL
4113  * 
4114  * Sets @attribute of type %G_FILE_ATTRIBUTE_TYPE_UINT32 to @value. 
4115  * If @attribute is of a different type, this operation will fail.
4116  * 
4117  * If @cancellable is not %NULL, then the operation can be cancelled by
4118  * triggering the cancellable object from another thread. If the operation
4119  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
4120  * 
4121  * Returns: %TRUE if the @attribute was successfully set to @value 
4122  * in the @file, %FALSE otherwise.
4123  **/
4124 gboolean
4125 g_file_set_attribute_uint32 (GFile                *file,
4126                              const char           *attribute,
4127                              guint32               value,
4128                              GFileQueryInfoFlags   flags,
4129                              GCancellable         *cancellable,
4130                              GError              **error)
4131 {
4132   return g_file_set_attribute (file, attribute,
4133                                G_FILE_ATTRIBUTE_TYPE_UINT32, &value,
4134                                flags, cancellable, error);
4135 }
4136
4137 /**
4138  * g_file_set_attribute_int32:
4139  * @file: input #GFile.
4140  * @attribute: a string containing the attribute's name.
4141  * @value: a #gint32 containing the attribute's new value.
4142  * @flags: a #GFileQueryInfoFlags.
4143  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4144  * @error: a #GError, or %NULL
4145  * 
4146  * Sets @attribute of type %G_FILE_ATTRIBUTE_TYPE_INT32 to @value. 
4147  * If @attribute is of a different type, this operation will fail.
4148  * 
4149  * If @cancellable is not %NULL, then the operation can be cancelled by
4150  * triggering the cancellable object from another thread. If the operation
4151  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
4152  * 
4153  * Returns: %TRUE if the @attribute was successfully set to @value 
4154  * in the @file, %FALSE otherwise. 
4155  **/
4156 gboolean
4157 g_file_set_attribute_int32 (GFile                *file,
4158                             const char           *attribute,
4159                             gint32                value,
4160                             GFileQueryInfoFlags   flags,
4161                             GCancellable         *cancellable,
4162                             GError              **error)
4163 {
4164   return g_file_set_attribute (file, attribute,
4165                                G_FILE_ATTRIBUTE_TYPE_INT32, &value,
4166                                flags, cancellable, error);
4167 }
4168
4169 /**
4170  * g_file_set_attribute_uint64:
4171  * @file: input #GFile. 
4172  * @attribute: a string containing the attribute's name.
4173  * @value: a #guint64 containing the attribute's new value.
4174  * @flags: a #GFileQueryInfoFlags.
4175  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4176  * @error: a #GError, or %NULL
4177  * 
4178  * Sets @attribute of type %G_FILE_ATTRIBUTE_TYPE_UINT64 to @value. 
4179  * If @attribute is of a different type, this operation will fail.
4180  * 
4181  * If @cancellable is not %NULL, then the operation can be cancelled by
4182  * triggering the cancellable object from another thread. If the operation
4183  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
4184  * 
4185  * Returns: %TRUE if the @attribute was successfully set to @value 
4186  * in the @file, %FALSE otherwise.
4187  **/
4188 gboolean
4189 g_file_set_attribute_uint64 (GFile                *file,
4190                              const char           *attribute,
4191                              guint64               value,
4192                              GFileQueryInfoFlags   flags,
4193                              GCancellable         *cancellable,
4194                              GError              **error)
4195  {
4196   return g_file_set_attribute (file, attribute,
4197                                G_FILE_ATTRIBUTE_TYPE_UINT64, &value,
4198                                flags, cancellable, error);
4199 }
4200
4201 /**
4202  * g_file_set_attribute_int64:
4203  * @file: input #GFile.
4204  * @attribute: a string containing the attribute's name.
4205  * @value: a #guint64 containing the attribute's new value.
4206  * @flags: a #GFileQueryInfoFlags.
4207  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4208  * @error: a #GError, or %NULL
4209  * 
4210  * Sets @attribute of type %G_FILE_ATTRIBUTE_TYPE_INT64 to @value. 
4211  * If @attribute is of a different type, this operation will fail.
4212  * 
4213  * If @cancellable is not %NULL, then the operation can be cancelled by
4214  * triggering the cancellable object from another thread. If the operation
4215  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
4216  * 
4217  * Returns: %TRUE if the @attribute was successfully set, %FALSE otherwise.
4218  **/
4219 gboolean
4220 g_file_set_attribute_int64 (GFile                *file,
4221                             const char           *attribute,
4222                             gint64                value,
4223                             GFileQueryInfoFlags   flags,
4224                             GCancellable         *cancellable,
4225                             GError              **error)
4226 {
4227   return g_file_set_attribute (file, attribute,
4228                                G_FILE_ATTRIBUTE_TYPE_INT64, &value,
4229                                flags, cancellable, error);
4230 }
4231
4232 /**
4233  * g_file_mount_mountable:
4234  * @file: input #GFile.
4235  * @flags: flags affecting the operation
4236  * @mount_operation: a #GMountOperation, or %NULL to avoid user interaction.
4237  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4238  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied, or %NULL.
4239  * @user_data: (closure): the data to pass to callback function
4240  * 
4241  * Mounts a file of type G_FILE_TYPE_MOUNTABLE.
4242  * Using @mount_operation, you can request callbacks when, for instance, 
4243  * passwords are needed during authentication.
4244  *
4245  * If @cancellable is not %NULL, then the operation can be cancelled by
4246  * triggering the cancellable object from another thread. If the operation
4247  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
4248  *
4249  * When the operation is finished, @callback will be called. You can then call
4250  * g_file_mount_mountable_finish() to get the result of the operation.
4251  **/
4252 void
4253 g_file_mount_mountable (GFile               *file,
4254                         GMountMountFlags     flags,
4255                         GMountOperation     *mount_operation,
4256                         GCancellable        *cancellable,
4257                         GAsyncReadyCallback  callback,
4258                         gpointer             user_data)
4259 {
4260   GFileIface *iface;
4261
4262   g_return_if_fail (G_IS_FILE (file));
4263
4264   iface = G_FILE_GET_IFACE (file);
4265
4266   if (iface->mount_mountable == NULL) 
4267     {
4268       g_simple_async_report_error_in_idle (G_OBJECT (file),
4269                                            callback,
4270                                            user_data,
4271                                            G_IO_ERROR,
4272                                            G_IO_ERROR_NOT_SUPPORTED,
4273                                            _("Operation not supported"));
4274       return;
4275     }
4276   
4277   (* iface->mount_mountable) (file,
4278                               flags,
4279                               mount_operation,
4280                               cancellable,
4281                               callback,
4282                               user_data);
4283 }
4284
4285 /**
4286  * g_file_mount_mountable_finish:
4287  * @file: input #GFile.
4288  * @result: a #GAsyncResult.
4289  * @error: a #GError, or %NULL
4290  *
4291  * Finishes a mount operation. See g_file_mount_mountable() for details.
4292  * 
4293  * Finish an asynchronous mount operation that was started 
4294  * with g_file_mount_mountable().
4295  *
4296  * Returns: (transfer full): a #GFile or %NULL on error.
4297  *     Free the returned object with g_object_unref().
4298  **/
4299 GFile *
4300 g_file_mount_mountable_finish (GFile         *file,
4301                                GAsyncResult  *result,
4302                                GError       **error)
4303 {
4304   GFileIface *iface;
4305
4306   g_return_val_if_fail (G_IS_FILE (file), NULL);
4307   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), NULL);
4308
4309   if (G_IS_SIMPLE_ASYNC_RESULT (result))
4310     {
4311       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
4312       if (g_simple_async_result_propagate_error (simple, error))
4313         return NULL;
4314     }
4315   
4316   iface = G_FILE_GET_IFACE (file);
4317   return (* iface->mount_mountable_finish) (file, result, error);
4318 }
4319
4320 /**
4321  * g_file_unmount_mountable:
4322  * @file: input #GFile.
4323  * @flags: flags affecting the operation
4324  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4325  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied, or %NULL.
4326  * @user_data: (closure): the data to pass to callback function
4327  *
4328  * Unmounts a file of type G_FILE_TYPE_MOUNTABLE.
4329  *
4330  * If @cancellable is not %NULL, then the operation can be cancelled by
4331  * triggering the cancellable object from another thread. If the operation
4332  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
4333  *
4334  * When the operation is finished, @callback will be called. You can then call
4335  * g_file_unmount_mountable_finish() to get the result of the operation.
4336  *
4337  * Deprecated: 2.22: Use g_file_unmount_mountable_with_operation() instead.
4338  **/
4339 void
4340 g_file_unmount_mountable (GFile               *file,
4341                           GMountUnmountFlags   flags,
4342                           GCancellable        *cancellable,
4343                           GAsyncReadyCallback  callback,
4344                           gpointer             user_data)
4345 {
4346   GFileIface *iface;
4347   
4348   g_return_if_fail (G_IS_FILE (file));
4349
4350   iface = G_FILE_GET_IFACE (file);
4351   
4352   if (iface->unmount_mountable == NULL)
4353     {
4354       g_simple_async_report_error_in_idle (G_OBJECT (file),
4355                                            callback,
4356                                            user_data,
4357                                            G_IO_ERROR,
4358                                            G_IO_ERROR_NOT_SUPPORTED,
4359                                            _("Operation not supported"));
4360       return;
4361     }
4362   
4363   (* iface->unmount_mountable) (file,
4364                                 flags,
4365                                 cancellable,
4366                                 callback,
4367                                 user_data);
4368 }
4369
4370 /**
4371  * g_file_unmount_mountable_finish:
4372  * @file: input #GFile.
4373  * @result: a #GAsyncResult.
4374  * @error: a #GError, or %NULL
4375  *
4376  * Finishes an unmount operation, see g_file_unmount_mountable() for details.
4377  * 
4378  * Finish an asynchronous unmount operation that was started 
4379  * with g_file_unmount_mountable().
4380  *
4381  * Returns: %TRUE if the operation finished successfully. %FALSE
4382  * otherwise.
4383  *
4384  * Deprecated: 2.22: Use g_file_unmount_mountable_with_operation_finish() instead.
4385  **/
4386 gboolean
4387 g_file_unmount_mountable_finish (GFile         *file,
4388                                  GAsyncResult  *result,
4389                                  GError       **error)
4390 {
4391   GFileIface *iface;
4392   
4393   g_return_val_if_fail (G_IS_FILE (file), FALSE);
4394   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), FALSE);
4395
4396   if (G_IS_SIMPLE_ASYNC_RESULT (result))
4397     {
4398       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
4399       if (g_simple_async_result_propagate_error (simple, error))
4400         return FALSE;
4401     }
4402   
4403   iface = G_FILE_GET_IFACE (file);
4404   return (* iface->unmount_mountable_finish) (file, result, error);
4405 }
4406
4407 /**
4408  * g_file_unmount_mountable_with_operation:
4409  * @file: input #GFile.
4410  * @flags: flags affecting the operation
4411  * @mount_operation: a #GMountOperation, or %NULL to avoid user interaction.
4412  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4413  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied, or %NULL.
4414  * @user_data: (closure): the data to pass to callback function
4415  *
4416  * Unmounts a file of type G_FILE_TYPE_MOUNTABLE.
4417  *
4418  * If @cancellable is not %NULL, then the operation can be cancelled by
4419  * triggering the cancellable object from another thread. If the operation
4420  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
4421  *
4422  * When the operation is finished, @callback will be called. You can then call
4423  * g_file_unmount_mountable_finish() to get the result of the operation.
4424  *
4425  * Since: 2.22
4426  **/
4427 void
4428 g_file_unmount_mountable_with_operation (GFile               *file,
4429                                          GMountUnmountFlags   flags,
4430                                          GMountOperation     *mount_operation,
4431                                          GCancellable        *cancellable,
4432                                          GAsyncReadyCallback  callback,
4433                                          gpointer             user_data)
4434 {
4435   GFileIface *iface;
4436
4437   g_return_if_fail (G_IS_FILE (file));
4438
4439   iface = G_FILE_GET_IFACE (file);
4440
4441   if (iface->unmount_mountable == NULL && iface->unmount_mountable_with_operation == NULL)
4442     {
4443       g_simple_async_report_error_in_idle (G_OBJECT (file),
4444                                            callback,
4445                                            user_data,
4446                                            G_IO_ERROR,
4447                                            G_IO_ERROR_NOT_SUPPORTED,
4448                                            _("Operation not supported"));
4449       return;
4450     }
4451
4452   if (iface->unmount_mountable_with_operation != NULL)
4453     (* iface->unmount_mountable_with_operation) (file,
4454                                                  flags,
4455                                                  mount_operation,
4456                                                  cancellable,
4457                                                  callback,
4458                                                  user_data);
4459   else
4460     (* iface->unmount_mountable) (file,
4461                                   flags,
4462                                   cancellable,
4463                                   callback,
4464                                   user_data);
4465 }
4466
4467 /**
4468  * g_file_unmount_mountable_with_operation_finish:
4469  * @file: input #GFile.
4470  * @result: a #GAsyncResult.
4471  * @error: a #GError, or %NULL
4472  *
4473  * Finishes an unmount operation, see g_file_unmount_mountable_with_operation() for details.
4474  *
4475  * Finish an asynchronous unmount operation that was started
4476  * with g_file_unmount_mountable_with_operation().
4477  *
4478  * Returns: %TRUE if the operation finished successfully. %FALSE
4479  * otherwise.
4480  *
4481  * Since: 2.22
4482  **/
4483 gboolean
4484 g_file_unmount_mountable_with_operation_finish (GFile         *file,
4485                                                 GAsyncResult  *result,
4486                                                 GError       **error)
4487 {
4488   GFileIface *iface;
4489
4490   g_return_val_if_fail (G_IS_FILE (file), FALSE);
4491   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), FALSE);
4492
4493   if (G_IS_SIMPLE_ASYNC_RESULT (result))
4494     {
4495       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
4496       if (g_simple_async_result_propagate_error (simple, error))
4497         return FALSE;
4498     }
4499
4500   iface = G_FILE_GET_IFACE (file);
4501   if (iface->unmount_mountable_with_operation_finish != NULL)
4502     return (* iface->unmount_mountable_with_operation_finish) (file, result, error);
4503   else
4504     return (* iface->unmount_mountable_finish) (file, result, error);
4505 }
4506
4507 /**
4508  * g_file_eject_mountable:
4509  * @file: input #GFile.
4510  * @flags: flags affecting the operation
4511  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4512  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied, or %NULL.
4513  * @user_data: (closure): the data to pass to callback function
4514  * 
4515  * Starts an asynchronous eject on a mountable.  
4516  * When this operation has completed, @callback will be called with
4517  * @user_user data, and the operation can be finalized with 
4518  * g_file_eject_mountable_finish().
4519  * 
4520  * If @cancellable is not %NULL, then the operation can be cancelled by
4521  * triggering the cancellable object from another thread. If the operation
4522  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
4523  *
4524  * Deprecated: 2.22: Use g_file_eject_mountable_with_operation() instead.
4525  **/
4526 void
4527 g_file_eject_mountable (GFile               *file,
4528                         GMountUnmountFlags   flags,
4529                         GCancellable        *cancellable,
4530                         GAsyncReadyCallback  callback,
4531                         gpointer             user_data)
4532 {
4533   GFileIface *iface;
4534
4535   g_return_if_fail (G_IS_FILE (file));
4536
4537   iface = G_FILE_GET_IFACE (file);
4538   
4539   if (iface->eject_mountable == NULL) 
4540     {
4541       g_simple_async_report_error_in_idle (G_OBJECT (file),
4542                                            callback,
4543                                            user_data,
4544                                            G_IO_ERROR,
4545                                            G_IO_ERROR_NOT_SUPPORTED,
4546                                            _("Operation not supported"));
4547       return;
4548     }
4549   
4550   (* iface->eject_mountable) (file,
4551                               flags,
4552                               cancellable,
4553                               callback,
4554                               user_data);
4555 }
4556
4557 /**
4558  * g_file_eject_mountable_finish:
4559  * @file: input #GFile.
4560  * @result: a #GAsyncResult.
4561  * @error: a #GError, or %NULL
4562  * 
4563  * Finishes an asynchronous eject operation started by 
4564  * g_file_eject_mountable().
4565  * 
4566  * Returns: %TRUE if the @file was ejected successfully. %FALSE 
4567  * otherwise.
4568  *
4569  * Deprecated: 2.22: Use g_file_eject_mountable_with_operation_finish() instead.
4570  **/
4571 gboolean
4572 g_file_eject_mountable_finish (GFile         *file,
4573                                GAsyncResult  *result,
4574                                GError       **error)
4575 {
4576   GFileIface *iface;
4577   
4578   g_return_val_if_fail (G_IS_FILE (file), FALSE);
4579   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), FALSE);
4580
4581   if (G_IS_SIMPLE_ASYNC_RESULT (result))
4582     {
4583       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
4584       if (g_simple_async_result_propagate_error (simple, error))
4585         return FALSE;
4586     }
4587   
4588   iface = G_FILE_GET_IFACE (file);
4589   return (* iface->eject_mountable_finish) (file, result, error);
4590 }
4591
4592 /**
4593  * g_file_eject_mountable_with_operation:
4594  * @file: input #GFile.
4595  * @flags: flags affecting the operation
4596  * @mount_operation: a #GMountOperation, or %NULL to avoid user interaction.
4597  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4598  * @callback: (scope async): a #GAsyncReadyCallback to call when the request is satisfied, or %NULL.
4599  * @user_data: (closure): the data to pass to callback function
4600  *
4601  * Starts an asynchronous eject on a mountable.
4602  * When this operation has completed, @callback will be called with
4603  * @user_user data, and the operation can be finalized with
4604  * g_file_eject_mountable_with_operation_finish().
4605  *
4606  * If @cancellable is not %NULL, then the operation can be cancelled by
4607  * triggering the cancellable object from another thread. If the operation
4608  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
4609  *
4610  * Since: 2.22
4611  **/
4612 void
4613 g_file_eject_mountable_with_operation (GFile               *file,
4614                                        GMountUnmountFlags   flags,
4615                                        GMountOperation     *mount_operation,
4616                                        GCancellable        *cancellable,
4617                                        GAsyncReadyCallback  callback,
4618                                        gpointer             user_data)
4619 {
4620   GFileIface *iface;
4621
4622   g_return_if_fail (G_IS_FILE (file));
4623
4624   iface = G_FILE_GET_IFACE (file);
4625
4626   if (iface->eject_mountable == NULL && iface->eject_mountable_with_operation == NULL)
4627     {
4628       g_simple_async_report_error_in_idle (G_OBJECT (file),
4629                                            callback,
4630                                            user_data,
4631                                            G_IO_ERROR,
4632                                            G_IO_ERROR_NOT_SUPPORTED,
4633                                            _("Operation not supported"));
4634       return;
4635     }
4636
4637   if (iface->eject_mountable_with_operation != NULL)
4638     (* iface->eject_mountable_with_operation) (file,
4639                                                flags,
4640                                                mount_operation,
4641                                                cancellable,
4642                                                callback,
4643                                                user_data);
4644   else
4645     (* iface->eject_mountable) (file,
4646                                 flags,
4647                                 cancellable,
4648                                 callback,
4649                                 user_data);
4650 }
4651
4652 /**
4653  * g_file_eject_mountable_with_operation_finish:
4654  * @file: input #GFile.
4655  * @result: a #GAsyncResult.
4656  * @error: a #GError, or %NULL
4657  *
4658  * Finishes an asynchronous eject operation started by
4659  * g_file_eject_mountable_with_operation().
4660  *
4661  * Returns: %TRUE if the @file was ejected successfully. %FALSE
4662  * otherwise.
4663  *
4664  * Since: 2.22
4665  **/
4666 gboolean
4667 g_file_eject_mountable_with_operation_finish (GFile         *file,
4668                                               GAsyncResult  *result,
4669                                               GError       **error)
4670 {
4671   GFileIface *iface;
4672
4673   g_return_val_if_fail (G_IS_FILE (file), FALSE);
4674   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), FALSE);
4675
4676   if (G_IS_SIMPLE_ASYNC_RESULT (result))
4677     {
4678       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
4679       if (g_simple_async_result_propagate_error (simple, error))
4680         return FALSE;
4681     }
4682
4683   iface = G_FILE_GET_IFACE (file);
4684   if (iface->eject_mountable_with_operation_finish != NULL)
4685     return (* iface->eject_mountable_with_operation_finish) (file, result, error);
4686   else
4687     return (* iface->eject_mountable_finish) (file, result, error);
4688 }
4689
4690 /**
4691  * g_file_monitor_directory:
4692  * @file: input #GFile.
4693  * @flags: a set of #GFileMonitorFlags.
4694  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4695  * @error: a #GError, or %NULL.
4696  * 
4697  * Obtains a directory monitor for the given file.
4698  * This may fail if directory monitoring is not supported.
4699  *
4700  * If @cancellable is not %NULL, then the operation can be cancelled by
4701  * triggering the cancellable object from another thread. If the operation
4702  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
4703  *
4704  * Virtual: monitor_dir
4705  * Returns: (transfer full): a #GFileMonitor for the given @file, or %NULL on error.
4706  *     Free the returned object with g_object_unref().
4707  **/
4708 GFileMonitor*
4709 g_file_monitor_directory (GFile             *file,
4710                           GFileMonitorFlags  flags,
4711                           GCancellable      *cancellable,
4712                           GError           **error)
4713 {
4714   GFileIface *iface;
4715
4716   g_return_val_if_fail (G_IS_FILE (file), NULL);
4717
4718   if (g_cancellable_set_error_if_cancelled (cancellable, error))
4719     return NULL;
4720
4721   iface = G_FILE_GET_IFACE (file);
4722
4723   if (iface->monitor_dir == NULL)
4724     {
4725       g_set_error_literal (error, G_IO_ERROR,
4726                            G_IO_ERROR_NOT_SUPPORTED,
4727                            _("Operation not supported"));
4728       return NULL;
4729     }
4730
4731   return (* iface->monitor_dir) (file, flags, cancellable, error);
4732 }
4733
4734 /**
4735  * g_file_monitor_file:
4736  * @file: input #GFile.
4737  * @flags: a set of #GFileMonitorFlags.
4738  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore.
4739  * @error: a #GError, or %NULL.
4740  * 
4741  * Obtains a file monitor for the given file. If no file notification
4742  * mechanism exists, then regular polling of the file is used.
4743  *
4744  * If @cancellable is not %NULL, then the operation can be cancelled by
4745  * triggering the cancellable object from another thread. If the operation
4746  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
4747  * 
4748  * Returns: (transfer full): a #GFileMonitor for the given @file, or %NULL on error.
4749  *     Free the returned object with g_object_unref().
4750  **/
4751 GFileMonitor*
4752 g_file_monitor_file (GFile             *file,
4753                      GFileMonitorFlags  flags,
4754                      GCancellable      *cancellable,
4755                      GError           **error)
4756 {
4757   GFileIface *iface;
4758   GFileMonitor *monitor;
4759   
4760   g_return_val_if_fail (G_IS_FILE (file), NULL);
4761
4762   if (g_cancellable_set_error_if_cancelled (cancellable, error))
4763     return NULL;
4764
4765   iface = G_FILE_GET_IFACE (file);
4766
4767   monitor = NULL;
4768   
4769   if (iface->monitor_file)
4770     monitor = (* iface->monitor_file) (file, flags, cancellable, NULL);
4771
4772 /* Fallback to polling */
4773   if (monitor == NULL)
4774     monitor = _g_poll_file_monitor_new (file);
4775
4776   return monitor;
4777 }
4778
4779 /**
4780  * g_file_monitor:
4781  * @file: input #GFile
4782  * @flags: a set of #GFileMonitorFlags
4783  * @cancellable: (allow-none): optional #GCancellable object, %NULL to ignore
4784  * @error: a #GError, or %NULL
4785  * 
4786  * Obtains a file or directory monitor for the given file, depending
4787  * on the type of the file.
4788  *
4789  * If @cancellable is not %NULL, then the operation can be cancelled by
4790  * triggering the cancellable object from another thread. If the operation
4791  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
4792  * 
4793  * Returns: (transfer full): a #GFileMonitor for the given @file, or %NULL on error.
4794  *     Free the returned object with g_object_unref().
4795  *
4796  * Since: 2.18
4797  */
4798 GFileMonitor*
4799 g_file_monitor (GFile             *file,
4800                 GFileMonitorFlags  flags,
4801                 GCancellable      *cancellable,
4802                 GError           **error)
4803 {
4804   if (g_file_query_file_type (file, 0, cancellable) == G_FILE_TYPE_DIRECTORY)
4805     return g_file_monitor_directory (file, flags, cancellable, error);
4806   else
4807     return g_file_monitor_file (file, flags, cancellable, error);
4808 }
4809
4810 /********************************************
4811  *   Default implementation of async ops    *
4812  ********************************************/
4813
4814 typedef struct {
4815   char *attributes;
4816   GFileQueryInfoFlags flags;
4817   GFileInfo *info;
4818 } QueryInfoAsyncData;
4819
4820 static void
4821 query_info_data_free (QueryInfoAsyncData *data)
4822 {
4823   if (data->info)
4824     g_object_unref (data->info);
4825   g_free (data->attributes);
4826   g_free (data);
4827 }
4828
4829 static void
4830 query_info_async_thread (GSimpleAsyncResult *res,
4831                          GObject            *object,
4832                          GCancellable       *cancellable)
4833 {
4834   GError *error = NULL;
4835   QueryInfoAsyncData *data;
4836   GFileInfo *info;
4837   
4838   data = g_simple_async_result_get_op_res_gpointer (res);
4839   
4840   info = g_file_query_info (G_FILE (object), data->attributes, data->flags, cancellable, &error);
4841
4842   if (info == NULL)
4843     g_simple_async_result_take_error (res, error);
4844   else
4845     data->info = info;
4846 }
4847
4848 static void
4849 g_file_real_query_info_async (GFile               *file,
4850                               const char          *attributes,
4851                               GFileQueryInfoFlags  flags,
4852                               int                  io_priority,
4853                               GCancellable        *cancellable,
4854                               GAsyncReadyCallback  callback,
4855                               gpointer             user_data)
4856 {
4857   GSimpleAsyncResult *res;
4858   QueryInfoAsyncData *data;
4859
4860   data = g_new0 (QueryInfoAsyncData, 1);
4861   data->attributes = g_strdup (attributes);
4862   data->flags = flags;
4863   
4864   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_query_info_async);
4865   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)query_info_data_free);
4866   
4867   g_simple_async_result_run_in_thread (res, query_info_async_thread, io_priority, cancellable);
4868   g_object_unref (res);
4869 }
4870
4871 static GFileInfo *
4872 g_file_real_query_info_finish (GFile         *file,
4873                                GAsyncResult  *res,
4874                                GError       **error)
4875 {
4876   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
4877   QueryInfoAsyncData *data;
4878
4879   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_query_info_async);
4880
4881   data = g_simple_async_result_get_op_res_gpointer (simple);
4882   if (data->info)
4883     return g_object_ref (data->info);
4884   
4885   return NULL;
4886 }
4887
4888 typedef struct {
4889   char *attributes;
4890   GFileInfo *info;
4891 } QueryFilesystemInfoAsyncData;
4892
4893 static void
4894 query_filesystem_info_data_free (QueryFilesystemInfoAsyncData *data)
4895 {
4896   if (data->info)
4897     g_object_unref (data->info);
4898   g_free (data->attributes);
4899   g_free (data);
4900 }
4901
4902 static void
4903 query_filesystem_info_async_thread (GSimpleAsyncResult *res,
4904                                     GObject            *object,
4905                                     GCancellable       *cancellable)
4906 {
4907   GError *error = NULL;
4908   QueryFilesystemInfoAsyncData *data;
4909   GFileInfo *info;
4910   
4911   data = g_simple_async_result_get_op_res_gpointer (res);
4912   
4913   info = g_file_query_filesystem_info (G_FILE (object), data->attributes, cancellable, &error);
4914
4915   if (info == NULL)
4916     g_simple_async_result_take_error (res, error);
4917   else
4918     data->info = info;
4919 }
4920
4921 static void
4922 g_file_real_query_filesystem_info_async (GFile               *file,
4923                                          const char          *attributes,
4924                                          int                  io_priority,
4925                                          GCancellable        *cancellable,
4926                                          GAsyncReadyCallback  callback,
4927                                          gpointer             user_data)
4928 {
4929   GSimpleAsyncResult *res;
4930   QueryFilesystemInfoAsyncData *data;
4931
4932   data = g_new0 (QueryFilesystemInfoAsyncData, 1);
4933   data->attributes = g_strdup (attributes);
4934   
4935   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_query_filesystem_info_async);
4936   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)query_filesystem_info_data_free);
4937   
4938   g_simple_async_result_run_in_thread (res, query_filesystem_info_async_thread, io_priority, cancellable);
4939   g_object_unref (res);
4940 }
4941
4942 static GFileInfo *
4943 g_file_real_query_filesystem_info_finish (GFile         *file,
4944                                           GAsyncResult  *res,
4945                                           GError       **error)
4946 {
4947   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
4948   QueryFilesystemInfoAsyncData *data;
4949
4950   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_query_filesystem_info_async);
4951
4952   data = g_simple_async_result_get_op_res_gpointer (simple);
4953   if (data->info)
4954     return g_object_ref (data->info);
4955   
4956   return NULL;
4957 }
4958
4959 typedef struct {
4960   char *attributes;
4961   GFileQueryInfoFlags flags;
4962   GFileEnumerator *enumerator;
4963 } EnumerateChildrenAsyncData;
4964
4965 static void
4966 enumerate_children_data_free (EnumerateChildrenAsyncData *data)
4967 {
4968   if (data->enumerator)
4969     g_object_unref (data->enumerator);
4970   g_free (data->attributes);
4971   g_free (data);
4972 }
4973
4974 static void
4975 enumerate_children_async_thread (GSimpleAsyncResult *res,
4976                                  GObject            *object,
4977                                  GCancellable       *cancellable)
4978 {
4979   GError *error = NULL;
4980   EnumerateChildrenAsyncData *data;
4981   GFileEnumerator *enumerator;
4982   
4983   data = g_simple_async_result_get_op_res_gpointer (res);
4984   
4985   enumerator = g_file_enumerate_children (G_FILE (object), data->attributes, data->flags, cancellable, &error);
4986
4987   if (enumerator == NULL)
4988     g_simple_async_result_take_error (res, error);
4989   else
4990     data->enumerator = enumerator;
4991 }
4992
4993 static void
4994 g_file_real_enumerate_children_async (GFile               *file,
4995                                       const char          *attributes,
4996                                       GFileQueryInfoFlags  flags,
4997                                       int                  io_priority,
4998                                       GCancellable        *cancellable,
4999                                       GAsyncReadyCallback  callback,
5000                                       gpointer             user_data)
5001 {
5002   GSimpleAsyncResult *res;
5003   EnumerateChildrenAsyncData *data;
5004
5005   data = g_new0 (EnumerateChildrenAsyncData, 1);
5006   data->attributes = g_strdup (attributes);
5007   data->flags = flags;
5008   
5009   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_enumerate_children_async);
5010   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)enumerate_children_data_free);
5011   
5012   g_simple_async_result_run_in_thread (res, enumerate_children_async_thread, io_priority, cancellable);
5013   g_object_unref (res);
5014 }
5015
5016 static GFileEnumerator *
5017 g_file_real_enumerate_children_finish (GFile         *file,
5018                                        GAsyncResult  *res,
5019                                        GError       **error)
5020 {
5021   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
5022   EnumerateChildrenAsyncData *data;
5023
5024   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_enumerate_children_async);
5025
5026   data = g_simple_async_result_get_op_res_gpointer (simple);
5027   if (data->enumerator)
5028     return g_object_ref (data->enumerator);
5029   
5030   return NULL;
5031 }
5032
5033 static void
5034 open_read_async_thread (GSimpleAsyncResult *res,
5035                         GObject            *object,
5036                         GCancellable       *cancellable)
5037 {
5038   GFileIface *iface;
5039   GFileInputStream *stream;
5040   GError *error = NULL;
5041
5042   iface = G_FILE_GET_IFACE (object);
5043
5044   if (iface->read_fn == NULL)
5045     {
5046       g_set_error_literal (&error, G_IO_ERROR,
5047                            G_IO_ERROR_NOT_SUPPORTED,
5048                            _("Operation not supported"));
5049
5050       g_simple_async_result_take_error (res, error);
5051
5052       return;
5053     }
5054   
5055   stream = iface->read_fn (G_FILE (object), cancellable, &error);
5056
5057   if (stream == NULL)
5058     g_simple_async_result_take_error (res, error);
5059   else
5060     g_simple_async_result_set_op_res_gpointer (res, stream, g_object_unref);
5061 }
5062
5063 static void
5064 g_file_real_read_async (GFile               *file,
5065                         int                  io_priority,
5066                         GCancellable        *cancellable,
5067                         GAsyncReadyCallback  callback,
5068                         gpointer             user_data)
5069 {
5070   GSimpleAsyncResult *res;
5071   
5072   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_read_async);
5073   
5074   g_simple_async_result_run_in_thread (res, open_read_async_thread, io_priority, cancellable);
5075   g_object_unref (res);
5076 }
5077
5078 static GFileInputStream *
5079 g_file_real_read_finish (GFile         *file,
5080                          GAsyncResult  *res,
5081                          GError       **error)
5082 {
5083   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
5084   gpointer op;
5085
5086   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_read_async);
5087
5088   op = g_simple_async_result_get_op_res_gpointer (simple);
5089   if (op)
5090     return g_object_ref (op);
5091   
5092   return NULL;
5093 }
5094
5095 static void
5096 append_to_async_thread (GSimpleAsyncResult *res,
5097                         GObject            *object,
5098                         GCancellable       *cancellable)
5099 {
5100   GFileIface *iface;
5101   GFileCreateFlags *data;
5102   GFileOutputStream *stream;
5103   GError *error = NULL;
5104
5105   iface = G_FILE_GET_IFACE (object);
5106
5107   data = g_simple_async_result_get_op_res_gpointer (res);
5108
5109   stream = iface->append_to (G_FILE (object), *data, cancellable, &error);
5110
5111   if (stream == NULL)
5112     g_simple_async_result_take_error (res, error);
5113   else
5114     g_simple_async_result_set_op_res_gpointer (res, stream, g_object_unref);
5115 }
5116
5117 static void
5118 g_file_real_append_to_async (GFile               *file,
5119                              GFileCreateFlags     flags,
5120                              int                  io_priority,
5121                              GCancellable        *cancellable,
5122                              GAsyncReadyCallback  callback,
5123                              gpointer             user_data)
5124 {
5125   GFileCreateFlags *data;
5126   GSimpleAsyncResult *res;
5127
5128   data = g_new0 (GFileCreateFlags, 1);
5129   *data = flags;
5130
5131   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_append_to_async);
5132   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)g_free);
5133
5134   g_simple_async_result_run_in_thread (res, append_to_async_thread, io_priority, cancellable);
5135   g_object_unref (res);
5136 }
5137
5138 static GFileOutputStream *
5139 g_file_real_append_to_finish (GFile         *file,
5140                               GAsyncResult  *res,
5141                               GError       **error)
5142 {
5143   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
5144   gpointer op;
5145
5146   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_append_to_async);
5147
5148   op = g_simple_async_result_get_op_res_gpointer (simple);
5149   if (op)
5150     return g_object_ref (op);
5151   
5152   return NULL;
5153 }
5154
5155 static void
5156 create_async_thread (GSimpleAsyncResult *res,
5157                      GObject            *object,
5158                      GCancellable       *cancellable)
5159 {
5160   GFileIface *iface;
5161   GFileCreateFlags *data;
5162   GFileOutputStream *stream;
5163   GError *error = NULL;
5164
5165   iface = G_FILE_GET_IFACE (object);
5166
5167   data = g_simple_async_result_get_op_res_gpointer (res);
5168
5169   stream = iface->create (G_FILE (object), *data, cancellable, &error);
5170
5171   if (stream == NULL)
5172     g_simple_async_result_take_error (res, error);
5173   else
5174     g_simple_async_result_set_op_res_gpointer (res, stream, g_object_unref);
5175 }
5176
5177 static void
5178 g_file_real_create_async (GFile               *file,
5179                           GFileCreateFlags     flags,
5180                           int                  io_priority,
5181                           GCancellable        *cancellable,
5182                           GAsyncReadyCallback  callback,
5183                           gpointer             user_data)
5184 {
5185   GFileCreateFlags *data;
5186   GSimpleAsyncResult *res;
5187
5188   data = g_new0 (GFileCreateFlags, 1);
5189   *data = flags;
5190
5191   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_create_async);
5192   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)g_free);
5193
5194   g_simple_async_result_run_in_thread (res, create_async_thread, io_priority, cancellable);
5195   g_object_unref (res);
5196 }
5197
5198 static GFileOutputStream *
5199 g_file_real_create_finish (GFile         *file,
5200                            GAsyncResult  *res,
5201                            GError       **error)
5202 {
5203   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
5204   gpointer op;
5205
5206   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_create_async);
5207
5208   op = g_simple_async_result_get_op_res_gpointer (simple);
5209   if (op)
5210     return g_object_ref (op);
5211   
5212   return NULL;
5213 }
5214
5215 typedef struct {
5216   GFileOutputStream *stream;
5217   char *etag;
5218   gboolean make_backup;
5219   GFileCreateFlags flags;
5220 } ReplaceAsyncData;
5221
5222 static void
5223 replace_async_data_free (ReplaceAsyncData *data)
5224 {
5225   if (data->stream)
5226     g_object_unref (data->stream);
5227   g_free (data->etag);
5228   g_free (data);
5229 }
5230
5231 static void
5232 replace_async_thread (GSimpleAsyncResult *res,
5233                       GObject            *object,
5234                       GCancellable       *cancellable)
5235 {
5236   GFileIface *iface;
5237   GFileOutputStream *stream;
5238   GError *error = NULL;
5239   ReplaceAsyncData *data;
5240
5241   iface = G_FILE_GET_IFACE (object);
5242   
5243   data = g_simple_async_result_get_op_res_gpointer (res);
5244
5245   stream = iface->replace (G_FILE (object),
5246                            data->etag,
5247                            data->make_backup,
5248                            data->flags,
5249                            cancellable,
5250                            &error);
5251
5252   if (stream == NULL)
5253     g_simple_async_result_take_error (res, error);
5254   else
5255     data->stream = stream;
5256 }
5257
5258 static void
5259 g_file_real_replace_async (GFile               *file,
5260                            const char          *etag,
5261                            gboolean             make_backup,
5262                            GFileCreateFlags     flags,
5263                            int                  io_priority,
5264                            GCancellable        *cancellable,
5265                            GAsyncReadyCallback  callback,
5266                            gpointer             user_data)
5267 {
5268   GSimpleAsyncResult *res;
5269   ReplaceAsyncData *data;
5270
5271   data = g_new0 (ReplaceAsyncData, 1);
5272   data->etag = g_strdup (etag);
5273   data->make_backup = make_backup;
5274   data->flags = flags;
5275
5276   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_replace_async);
5277   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)replace_async_data_free);
5278
5279   g_simple_async_result_run_in_thread (res, replace_async_thread, io_priority, cancellable);
5280   g_object_unref (res);
5281 }
5282
5283 static GFileOutputStream *
5284 g_file_real_replace_finish (GFile         *file,
5285                             GAsyncResult  *res,
5286                             GError       **error)
5287 {
5288   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
5289   ReplaceAsyncData *data;
5290
5291   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_replace_async);
5292
5293   data = g_simple_async_result_get_op_res_gpointer (simple);
5294   if (data->stream)
5295     return g_object_ref (data->stream);
5296   
5297   return NULL;
5298 }
5299
5300 static void
5301 open_readwrite_async_thread (GSimpleAsyncResult *res,
5302                              GObject            *object,
5303                              GCancellable       *cancellable)
5304 {
5305   GFileIface *iface;
5306   GFileIOStream *stream;
5307   GError *error = NULL;
5308
5309   iface = G_FILE_GET_IFACE (object);
5310
5311   if (iface->open_readwrite == NULL)
5312     {
5313       g_set_error_literal (&error, G_IO_ERROR,
5314                            G_IO_ERROR_NOT_SUPPORTED,
5315                            _("Operation not supported"));
5316
5317       g_simple_async_result_take_error (res, error);
5318
5319       return;
5320     }
5321
5322   stream = iface->open_readwrite (G_FILE (object), cancellable, &error);
5323
5324   if (stream == NULL)
5325     g_simple_async_result_take_error (res, error);
5326   else
5327     g_simple_async_result_set_op_res_gpointer (res, stream, g_object_unref);
5328 }
5329
5330 static void
5331 g_file_real_open_readwrite_async (GFile               *file,
5332                                   int                  io_priority,
5333                                   GCancellable        *cancellable,
5334                                   GAsyncReadyCallback  callback,
5335                                   gpointer             user_data)
5336 {
5337   GSimpleAsyncResult *res;
5338
5339   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_open_readwrite_async);
5340
5341   g_simple_async_result_run_in_thread (res, open_readwrite_async_thread, io_priority, cancellable);
5342   g_object_unref (res);
5343 }
5344
5345 static GFileIOStream *
5346 g_file_real_open_readwrite_finish (GFile         *file,
5347                                    GAsyncResult  *res,
5348                                    GError       **error)
5349 {
5350   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
5351   gpointer op;
5352
5353   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_open_readwrite_async);
5354
5355   op = g_simple_async_result_get_op_res_gpointer (simple);
5356   if (op)
5357     return g_object_ref (op);
5358
5359   return NULL;
5360 }
5361
5362 static void
5363 create_readwrite_async_thread (GSimpleAsyncResult *res,
5364                                GObject            *object,
5365                                GCancellable       *cancellable)
5366 {
5367   GFileIface *iface;
5368   GFileCreateFlags *data;
5369   GFileIOStream *stream;
5370   GError *error = NULL;
5371
5372   iface = G_FILE_GET_IFACE (object);
5373
5374   data = g_simple_async_result_get_op_res_gpointer (res);
5375
5376   if (iface->create_readwrite == NULL)
5377     {
5378       g_set_error_literal (&error, G_IO_ERROR,
5379                            G_IO_ERROR_NOT_SUPPORTED,
5380                            _("Operation not supported"));
5381
5382       g_simple_async_result_take_error (res, error);
5383
5384       return;
5385     }
5386
5387   stream = iface->create_readwrite (G_FILE (object), *data, cancellable, &error);
5388
5389   if (stream == NULL)
5390     g_simple_async_result_take_error (res, error);
5391   else
5392     g_simple_async_result_set_op_res_gpointer (res, stream, g_object_unref);
5393 }
5394
5395 static void
5396 g_file_real_create_readwrite_async (GFile               *file,
5397                                     GFileCreateFlags     flags,
5398                                     int                  io_priority,
5399                                     GCancellable        *cancellable,
5400                                     GAsyncReadyCallback  callback,
5401                                     gpointer             user_data)
5402 {
5403   GFileCreateFlags *data;
5404   GSimpleAsyncResult *res;
5405
5406   data = g_new0 (GFileCreateFlags, 1);
5407   *data = flags;
5408
5409   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_create_readwrite_async);
5410   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)g_free);
5411
5412   g_simple_async_result_run_in_thread (res, create_readwrite_async_thread, io_priority, cancellable);
5413   g_object_unref (res);
5414 }
5415
5416 static GFileIOStream *
5417 g_file_real_create_readwrite_finish (GFile         *file,
5418                                      GAsyncResult  *res,
5419                                      GError       **error)
5420 {
5421   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
5422   gpointer op;
5423
5424   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_create_readwrite_async);
5425
5426   op = g_simple_async_result_get_op_res_gpointer (simple);
5427   if (op)
5428     return g_object_ref (op);
5429
5430   return NULL;
5431 }
5432
5433 typedef struct {
5434   GFileIOStream *stream;
5435   char *etag;
5436   gboolean make_backup;
5437   GFileCreateFlags flags;
5438 } ReplaceRWAsyncData;
5439
5440 static void
5441 replace_rw_async_data_free (ReplaceRWAsyncData *data)
5442 {
5443   if (data->stream)
5444     g_object_unref (data->stream);
5445   g_free (data->etag);
5446   g_free (data);
5447 }
5448
5449 static void
5450 replace_readwrite_async_thread (GSimpleAsyncResult *res,
5451                                 GObject            *object,
5452                                 GCancellable       *cancellable)
5453 {
5454   GFileIface *iface;
5455   GFileIOStream *stream;
5456   GError *error = NULL;
5457   ReplaceRWAsyncData *data;
5458
5459   iface = G_FILE_GET_IFACE (object);
5460
5461   data = g_simple_async_result_get_op_res_gpointer (res);
5462
5463   stream = iface->replace_readwrite (G_FILE (object),
5464                                      data->etag,
5465                                      data->make_backup,
5466                                      data->flags,
5467                                      cancellable,
5468                                      &error);
5469
5470   if (stream == NULL)
5471     g_simple_async_result_take_error (res, error);
5472   else
5473     data->stream = stream;
5474 }
5475
5476 static void
5477 g_file_real_replace_readwrite_async (GFile               *file,
5478                                      const char          *etag,
5479                                      gboolean             make_backup,
5480                                      GFileCreateFlags     flags,
5481                                      int                  io_priority,
5482                                      GCancellable        *cancellable,
5483                                      GAsyncReadyCallback  callback,
5484                                      gpointer             user_data)
5485 {
5486   GSimpleAsyncResult *res;
5487   ReplaceRWAsyncData *data;
5488
5489   data = g_new0 (ReplaceRWAsyncData, 1);
5490   data->etag = g_strdup (etag);
5491   data->make_backup = make_backup;
5492   data->flags = flags;
5493
5494   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_replace_readwrite_async);
5495   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)replace_rw_async_data_free);
5496
5497   g_simple_async_result_run_in_thread (res, replace_readwrite_async_thread, io_priority, cancellable);
5498   g_object_unref (res);
5499 }
5500
5501 static GFileIOStream *
5502 g_file_real_replace_readwrite_finish (GFile         *file,
5503                                       GAsyncResult  *res,
5504                                       GError       **error)
5505 {
5506   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
5507   ReplaceRWAsyncData *data;
5508
5509   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_replace_readwrite_async);
5510
5511   data = g_simple_async_result_get_op_res_gpointer (simple);
5512   if (data->stream)
5513     return g_object_ref (data->stream);
5514
5515   return NULL;
5516 }
5517
5518 typedef struct {
5519   char *name;
5520   GFile *file;
5521 } SetDisplayNameAsyncData;
5522
5523 static void
5524 set_display_name_data_free (SetDisplayNameAsyncData *data)
5525 {
5526   g_free (data->name);
5527   if (data->file)
5528     g_object_unref (data->file);
5529   g_free (data);
5530 }
5531
5532 static void
5533 set_display_name_async_thread (GSimpleAsyncResult *res,
5534                                GObject            *object,
5535                                GCancellable       *cancellable)
5536 {
5537   GError *error = NULL;
5538   SetDisplayNameAsyncData *data;
5539   GFile *file;
5540   
5541   data = g_simple_async_result_get_op_res_gpointer (res);
5542   
5543   file = g_file_set_display_name (G_FILE (object), data->name, cancellable, &error);
5544
5545   if (file == NULL)
5546     g_simple_async_result_take_error (res, error);
5547   else
5548     data->file = file;
5549 }
5550
5551 static void
5552 g_file_real_set_display_name_async (GFile               *file,  
5553                                     const char          *display_name,
5554                                     int                  io_priority,
5555                                     GCancellable        *cancellable,
5556                                     GAsyncReadyCallback  callback,
5557                                     gpointer             user_data)
5558 {
5559   GSimpleAsyncResult *res;
5560   SetDisplayNameAsyncData *data;
5561
5562   data = g_new0 (SetDisplayNameAsyncData, 1);
5563   data->name = g_strdup (display_name);
5564   
5565   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_set_display_name_async);
5566   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)set_display_name_data_free);
5567   
5568   g_simple_async_result_run_in_thread (res, set_display_name_async_thread, io_priority, cancellable);
5569   g_object_unref (res);
5570 }
5571
5572 static GFile *
5573 g_file_real_set_display_name_finish (GFile         *file,
5574                                      GAsyncResult  *res,
5575                                      GError       **error)
5576 {
5577   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
5578   SetDisplayNameAsyncData *data;
5579
5580   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_set_display_name_async);
5581
5582   data = g_simple_async_result_get_op_res_gpointer (simple);
5583   if (data->file)
5584     return g_object_ref (data->file);
5585   
5586   return NULL;
5587 }
5588
5589 typedef struct {
5590   GFileQueryInfoFlags flags;
5591   GFileInfo *info;
5592   gboolean res;
5593   GError *error;
5594 } SetInfoAsyncData;
5595
5596 static void
5597 set_info_data_free (SetInfoAsyncData *data)
5598 {
5599   if (data->info)
5600     g_object_unref (data->info);
5601   if (data->error)
5602     g_error_free (data->error);
5603   g_free (data);
5604 }
5605
5606 static void
5607 set_info_async_thread (GSimpleAsyncResult *res,
5608                        GObject            *object,
5609                        GCancellable       *cancellable)
5610 {
5611   SetInfoAsyncData *data;
5612   
5613   data = g_simple_async_result_get_op_res_gpointer (res);
5614   
5615   data->error = NULL;
5616   data->res = g_file_set_attributes_from_info (G_FILE (object),
5617                                                data->info,
5618                                                data->flags,
5619                                                cancellable,
5620                                                &data->error);
5621 }
5622
5623 static void
5624 g_file_real_set_attributes_async (GFile               *file,
5625                                   GFileInfo           *info,
5626                                   GFileQueryInfoFlags  flags,
5627                                   int                  io_priority,
5628                                   GCancellable        *cancellable,
5629                                   GAsyncReadyCallback  callback,
5630                                   gpointer             user_data)
5631 {
5632   GSimpleAsyncResult *res;
5633   SetInfoAsyncData *data;
5634
5635   data = g_new0 (SetInfoAsyncData, 1);
5636   data->info = g_file_info_dup (info);
5637   data->flags = flags;
5638   
5639   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_set_attributes_async);
5640   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)set_info_data_free);
5641   
5642   g_simple_async_result_run_in_thread (res, set_info_async_thread, io_priority, cancellable);
5643   g_object_unref (res);
5644 }
5645
5646 static gboolean
5647 g_file_real_set_attributes_finish (GFile         *file,
5648                                    GAsyncResult  *res,
5649                                    GFileInfo    **info,
5650                                    GError       **error)
5651 {
5652   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
5653   SetInfoAsyncData *data;
5654   
5655   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_set_attributes_async);
5656
5657   data = g_simple_async_result_get_op_res_gpointer (simple);
5658
5659   if (info) 
5660     *info = g_object_ref (data->info);
5661
5662   if (error != NULL && data->error) 
5663     *error = g_error_copy (data->error);
5664   
5665   return data->res;
5666 }
5667
5668 static void
5669 find_enclosing_mount_async_thread (GSimpleAsyncResult *res,
5670                                     GObject            *object,
5671                                     GCancellable       *cancellable)
5672 {
5673   GError *error = NULL;
5674   GMount *mount;
5675   
5676   mount = g_file_find_enclosing_mount (G_FILE (object), cancellable, &error);
5677
5678   if (mount == NULL)
5679     g_simple_async_result_take_error (res, error);
5680   else
5681     g_simple_async_result_set_op_res_gpointer (res, mount, (GDestroyNotify)g_object_unref);
5682 }
5683
5684 static void
5685 g_file_real_find_enclosing_mount_async (GFile               *file,
5686                                         int                  io_priority,
5687                                         GCancellable        *cancellable,
5688                                         GAsyncReadyCallback  callback,
5689                                         gpointer             user_data)
5690 {
5691   GSimpleAsyncResult *res;
5692   
5693   res = g_simple_async_result_new (G_OBJECT (file), callback, user_data, g_file_real_find_enclosing_mount_async);
5694   
5695   g_simple_async_result_run_in_thread (res, find_enclosing_mount_async_thread, io_priority, cancellable);
5696   g_object_unref (res);
5697 }
5698
5699 static GMount *
5700 g_file_real_find_enclosing_mount_finish (GFile         *file,
5701                                           GAsyncResult  *res,
5702                                           GError       **error)
5703 {
5704   GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (res);
5705   GMount *mount;
5706
5707   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_real_find_enclosing_mount_async);
5708
5709   mount = g_simple_async_result_get_op_res_gpointer (simple);
5710   return g_object_ref (mount);
5711 }
5712
5713
5714 typedef struct {
5715   GFile *source;
5716   GFile *destination;
5717   GFileCopyFlags flags;
5718   GFileProgressCallback progress_cb;
5719   gpointer progress_cb_data;
5720   GIOSchedulerJob *job;
5721 } CopyAsyncData;
5722
5723 static void
5724 copy_async_data_free (CopyAsyncData *data)
5725 {
5726   g_object_unref (data->source);
5727   g_object_unref (data->destination);
5728   g_free (data);
5729 }
5730
5731 typedef struct {
5732   CopyAsyncData *data;
5733   goffset current_num_bytes;
5734   goffset total_num_bytes;
5735 } ProgressData;
5736
5737 static gboolean
5738 copy_async_progress_in_main (gpointer user_data)
5739 {
5740   ProgressData *progress = user_data;
5741   CopyAsyncData *data = progress->data;
5742
5743   data->progress_cb (progress->current_num_bytes,
5744                      progress->total_num_bytes,
5745                      data->progress_cb_data);
5746
5747   return FALSE;
5748 }
5749
5750 static gboolean
5751 mainloop_barrier (gpointer user_data)
5752 {
5753   /* Does nothing, but ensures all queued idles before
5754      this are run */
5755   return FALSE;
5756 }
5757
5758
5759 static void
5760 copy_async_progress_callback (goffset  current_num_bytes,
5761                               goffset  total_num_bytes,
5762                               gpointer user_data)
5763 {
5764   CopyAsyncData *data = user_data;
5765   ProgressData *progress;
5766
5767   progress = g_new (ProgressData, 1);
5768   progress->data = data;
5769   progress->current_num_bytes = current_num_bytes;
5770   progress->total_num_bytes = total_num_bytes;
5771   
5772   g_io_scheduler_job_send_to_mainloop_async (data->job,
5773                                              copy_async_progress_in_main,
5774                                              progress,
5775                                              g_free);
5776 }
5777
5778 static gboolean
5779 copy_async_thread (GIOSchedulerJob *job,
5780                    GCancellable    *cancellable,
5781                    gpointer         user_data)
5782 {
5783   GSimpleAsyncResult *res;
5784   CopyAsyncData *data;
5785   gboolean result;
5786   GError *error;
5787
5788   res = user_data;
5789   data = g_simple_async_result_get_op_res_gpointer (res);
5790
5791   error = NULL;
5792   data->job = job;
5793   result = g_file_copy (data->source,
5794                         data->destination,
5795                         data->flags,
5796                         cancellable,
5797                         (data->progress_cb != NULL) ? copy_async_progress_callback : NULL,
5798                         data,
5799                         &error);
5800
5801   /* Ensure all progress callbacks are done running in main thread */
5802   if (data->progress_cb != NULL)
5803     g_io_scheduler_job_send_to_mainloop (job,
5804                                          mainloop_barrier,
5805                                          NULL, NULL);
5806   
5807   if (!result)
5808     g_simple_async_result_take_error (res, error);
5809
5810   g_simple_async_result_complete_in_idle (res);
5811
5812   return FALSE;
5813 }
5814
5815 static void
5816 g_file_real_copy_async (GFile                  *source,
5817                         GFile                  *destination,
5818                         GFileCopyFlags          flags,
5819                         int                     io_priority,
5820                         GCancellable           *cancellable,
5821                         GFileProgressCallback   progress_callback,
5822                         gpointer                progress_callback_data,
5823                         GAsyncReadyCallback     callback,
5824                         gpointer                user_data)
5825 {
5826   GSimpleAsyncResult *res;
5827   CopyAsyncData *data;
5828
5829   data = g_new0 (CopyAsyncData, 1);
5830   data->source = g_object_ref (source);
5831   data->destination = g_object_ref (destination);
5832   data->flags = flags;
5833   data->progress_cb = progress_callback;
5834   data->progress_cb_data = progress_callback_data;
5835
5836   res = g_simple_async_result_new (G_OBJECT (source), callback, user_data, g_file_real_copy_async);
5837   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)copy_async_data_free);
5838
5839   g_io_scheduler_push_job (copy_async_thread, res, g_object_unref, io_priority, cancellable);
5840 }
5841
5842 static gboolean
5843 g_file_real_copy_finish (GFile        *file,
5844                          GAsyncResult *res,
5845                          GError      **error)
5846 {
5847   /* Error handled in g_file_copy_finish() */
5848   return TRUE;
5849 }
5850
5851
5852 /********************************************
5853  *   Default VFS operations                 *
5854  ********************************************/
5855
5856 /**
5857  * g_file_new_for_path:
5858  * @path: a string containing a relative or absolute path. The string
5859  *   must be encoded in the glib filename encoding.
5860  * 
5861  * Constructs a #GFile for a given path. This operation never
5862  * fails, but the returned object might not support any I/O
5863  * operation if @path is malformed.
5864  * 
5865  * Returns: (transfer full): a new #GFile for the given @path.
5866  *   Free the returned object with g_object_unref().
5867  **/
5868 GFile *
5869 g_file_new_for_path (const char *path)
5870 {
5871   g_return_val_if_fail (path != NULL, NULL);
5872
5873   return g_vfs_get_file_for_path (g_vfs_get_default (), path);
5874 }
5875  
5876 /**
5877  * g_file_new_for_uri:
5878  * @uri: a UTF8 string containing a URI.
5879  * 
5880  * Constructs a #GFile for a given URI. This operation never 
5881  * fails, but the returned object might not support any I/O 
5882  * operation if @uri is malformed or if the uri type is 
5883  * not supported.
5884  * 
5885  * Returns: (transfer full): a new #GFile for the given @uri.
5886  *   Free the returned object with g_object_unref().
5887  **/ 
5888 GFile *
5889 g_file_new_for_uri (const char *uri)
5890 {
5891   g_return_val_if_fail (uri != NULL, NULL);
5892
5893   return g_vfs_get_file_for_uri (g_vfs_get_default (), uri);
5894 }
5895
5896 /**
5897  * g_file_new_tmp:
5898  * @tmpl: (type filename) (allow-none): Template for the file
5899  *   name, as in g_file_open_tmp(), or %NULL for a default template.
5900  * @iostream: (out): on return, a #GFileIOStream for the created file.
5901  * @error: a #GError, or %NULL
5902  *
5903  * Opens a file in the preferred directory for temporary files (as
5904  * returned by g_get_tmp_dir()) and returns a #GFile and
5905  * #GFileIOStream pointing to it.
5906  *
5907  * @template should be a string in the GLib file name encoding
5908  * containing a sequence of six 'X' characters, and containing no
5909  * directory components. If it is %NULL, a default template is used.
5910  *
5911  * Unlike the other #GFile constructors, this will return %NULL if
5912  * a temporary file could not be created.
5913  *
5914  * Returns: (transfer full): a new #GFile.
5915  *   Free the returned object with g_object_unref().
5916  **/
5917 GFile *
5918 g_file_new_tmp (const char     *tmpl,
5919                 GFileIOStream **iostream,
5920                 GError        **error)
5921 {
5922   gint fd;
5923   gchar *path;
5924   GFile *file;
5925   GFileOutputStream *output;
5926
5927   g_return_val_if_fail (tmpl != NULL, NULL);
5928   g_return_val_if_fail (iostream != NULL, NULL);
5929
5930   fd = g_file_open_tmp (tmpl, &path, error);
5931   if (fd == -1)
5932     return NULL;
5933
5934   file = g_file_new_for_path (path);
5935
5936   output = _g_local_file_output_stream_new (fd);
5937   *iostream = _g_local_file_io_stream_new (G_LOCAL_FILE_OUTPUT_STREAM (output));
5938
5939   g_object_unref (output);
5940   g_free (path);
5941
5942   return file;
5943 }
5944
5945 /**
5946  * g_file_parse_name:
5947  * @parse_name: a file name or path to be parsed.
5948  * 
5949  * Constructs a #GFile with the given @parse_name (i.e. something given by g_file_get_parse_name()).
5950  * This operation never fails, but the returned object might not support any I/O
5951  * operation if the @parse_name cannot be parsed.
5952  * 
5953  * Returns: (transfer full): a new #GFile.
5954  **/
5955 GFile *
5956 g_file_parse_name (const char *parse_name)
5957 {
5958   g_return_val_if_fail (parse_name != NULL, NULL);
5959
5960   return g_vfs_parse_name (g_vfs_get_default (), parse_name);
5961 }
5962
5963 static gboolean
5964 is_valid_scheme_character (char c)
5965 {
5966   return g_ascii_isalnum (c) || c == '+' || c == '-' || c == '.';
5967 }
5968
5969 /* Following RFC 2396, valid schemes are built like:
5970  *       scheme        = alpha *( alpha | digit | "+" | "-" | "." )
5971  */
5972 static gboolean
5973 has_valid_scheme (const char *uri)
5974 {
5975   const char *p;
5976   
5977   p = uri;
5978   
5979   if (!g_ascii_isalpha (*p))
5980     return FALSE;
5981
5982   do {
5983     p++;
5984   } while (is_valid_scheme_character (*p));
5985
5986   return *p == ':';
5987 }
5988
5989 /**
5990  * g_file_new_for_commandline_arg:
5991  * @arg: a command line string.
5992  * 
5993  * Creates a #GFile with the given argument from the command line. The value of
5994  * @arg can be either a URI, an absolute path or a relative path resolved
5995  * relative to the current working directory.
5996  * This operation never fails, but the returned object might not support any
5997  * I/O operation if @arg points to a malformed path.
5998  *
5999  * Returns: (transfer full): a new #GFile.
6000  *  Free the returned object with g_object_unref().
6001  **/
6002 GFile *
6003 g_file_new_for_commandline_arg (const char *arg)
6004 {
6005   GFile *file;
6006   char *filename;
6007   char *current_dir;
6008   
6009   g_return_val_if_fail (arg != NULL, NULL);
6010   
6011   if (g_path_is_absolute (arg))
6012     return g_file_new_for_path (arg);
6013
6014   if (has_valid_scheme (arg))
6015     return g_file_new_for_uri (arg);
6016     
6017   current_dir = g_get_current_dir ();
6018   filename = g_build_filename (current_dir, arg, NULL);
6019   g_free (current_dir);
6020   
6021   file = g_file_new_for_path (filename);
6022   g_free (filename);
6023   
6024   return file;
6025 }
6026
6027 /**
6028  * g_file_mount_enclosing_volume:
6029  * @location: input #GFile.
6030  * @flags: flags affecting the operation
6031  * @mount_operation: a #GMountOperation or %NULL to avoid user interaction.
6032  * @cancellable: optional #GCancellable object, %NULL to ignore.
6033  * @callback: a #GAsyncReadyCallback to call when the request is satisfied, or %NULL.
6034  * @user_data: the data to pass to callback function
6035  * 
6036  * Starts a @mount_operation, mounting the volume that contains the file @location. 
6037  * 
6038  * When this operation has completed, @callback will be called with
6039  * @user_user data, and the operation can be finalized with 
6040  * g_file_mount_enclosing_volume_finish().
6041  * 
6042  * If @cancellable is not %NULL, then the operation can be cancelled by
6043  * triggering the cancellable object from another thread. If the operation
6044  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
6045  **/
6046 void
6047 g_file_mount_enclosing_volume (GFile               *location,
6048                                GMountMountFlags     flags,
6049                                GMountOperation     *mount_operation,
6050                                GCancellable        *cancellable,
6051                                GAsyncReadyCallback  callback,
6052                                gpointer             user_data)
6053 {
6054   GFileIface *iface;
6055
6056   g_return_if_fail (G_IS_FILE (location));
6057
6058   iface = G_FILE_GET_IFACE (location);
6059
6060   if (iface->mount_enclosing_volume == NULL)
6061     {
6062       g_simple_async_report_error_in_idle (G_OBJECT (location),
6063                                            callback, user_data,
6064                                            G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
6065                                            _("volume doesn't implement mount"));
6066       
6067       return;
6068     }
6069   
6070   (* iface->mount_enclosing_volume) (location, flags, mount_operation, cancellable, callback, user_data);
6071
6072 }
6073
6074 /**
6075  * g_file_mount_enclosing_volume_finish:
6076  * @location: input #GFile.
6077  * @result: a #GAsyncResult.
6078  * @error: a #GError, or %NULL
6079  * 
6080  * Finishes a mount operation started by g_file_mount_enclosing_volume().
6081  * 
6082  * Returns: %TRUE if successful. If an error
6083  * has occurred, this function will return %FALSE and set @error
6084  * appropriately if present.
6085  **/
6086 gboolean
6087 g_file_mount_enclosing_volume_finish (GFile         *location,
6088                                       GAsyncResult  *result,
6089                                       GError       **error)
6090 {
6091   GFileIface *iface;
6092
6093   g_return_val_if_fail (G_IS_FILE (location), FALSE);
6094   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), FALSE);
6095
6096   if (G_IS_SIMPLE_ASYNC_RESULT (result))
6097     {
6098       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
6099       if (g_simple_async_result_propagate_error (simple, error))
6100         return FALSE;
6101     }
6102   
6103   iface = G_FILE_GET_IFACE (location);
6104
6105   return (* iface->mount_enclosing_volume_finish) (location, result, error);
6106 }
6107
6108 /********************************************
6109  *   Utility functions                      *
6110  ********************************************/
6111
6112 /**
6113  * g_file_query_default_handler:
6114  * @file: a #GFile to open.
6115  * @cancellable: optional #GCancellable object, %NULL to ignore.
6116  * @error: a #GError, or %NULL
6117  *
6118  * Returns the #GAppInfo that is registered as the default
6119  * application to handle the file specified by @file.
6120  *
6121  * If @cancellable is not %NULL, then the operation can be cancelled by
6122  * triggering the cancellable object from another thread. If the operation
6123  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
6124  *
6125  * Returns: (transfer full): a #GAppInfo if the handle was found, %NULL if there were errors.
6126  * When you are done with it, release it with g_object_unref()
6127  **/
6128 GAppInfo *
6129 g_file_query_default_handler (GFile                  *file,
6130                               GCancellable           *cancellable,
6131                               GError                **error)
6132 {
6133   char *uri_scheme;
6134   const char *content_type;
6135   GAppInfo *appinfo;
6136   GFileInfo *info;
6137   char *path;
6138   
6139   uri_scheme = g_file_get_uri_scheme (file);
6140   if (uri_scheme && uri_scheme[0] != '\0')
6141     {
6142       appinfo = g_app_info_get_default_for_uri_scheme (uri_scheme);
6143       g_free (uri_scheme);
6144
6145       if (appinfo != NULL)
6146         return appinfo;
6147     }
6148
6149   info = g_file_query_info (file,
6150                             G_FILE_ATTRIBUTE_STANDARD_CONTENT_TYPE,
6151                             0,
6152                             cancellable,
6153                             error);
6154   if (info == NULL)
6155     return NULL;
6156
6157   appinfo = NULL;
6158
6159   content_type = g_file_info_get_content_type (info);
6160   if (content_type)
6161     {
6162       /* Don't use is_native(), as we want to support fuse paths if available */
6163       path = g_file_get_path (file);
6164       appinfo = g_app_info_get_default_for_type (content_type,
6165                                                  path == NULL);
6166       g_free (path);
6167     }
6168   
6169   g_object_unref (info);
6170
6171   if (appinfo != NULL)
6172     return appinfo;
6173
6174   g_set_error_literal (error, G_IO_ERROR,
6175                        G_IO_ERROR_NOT_SUPPORTED,
6176                        _("No application is registered as handling this file"));
6177   return NULL;
6178   
6179 }
6180
6181
6182 #define GET_CONTENT_BLOCK_SIZE 8192
6183
6184 /**
6185  * g_file_load_contents:
6186  * @file: input #GFile.
6187  * @cancellable: optional #GCancellable object, %NULL to ignore.
6188  * @contents: (out) (transfer full) (element-type guint8) (array length=length): a location to place the contents of the file.
6189  * @length: (out) (allow-none): a location to place the length of the contents of the file,
6190  *    or %NULL if the length is not needed
6191  * @etag_out: (out) (allow-none): a location to place the current entity tag for the file,
6192  *    or %NULL if the entity tag is not needed
6193  * @error: a #GError, or %NULL
6194  *
6195  * Loads the content of the file into memory. The data is always 
6196  * zero-terminated, but this is not included in the resultant @length.
6197  * The returned @content should be freed with g_free() when no longer
6198  * needed.
6199  * 
6200  * If @cancellable is not %NULL, then the operation can be cancelled by
6201  * triggering the cancellable object from another thread. If the operation
6202  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
6203  * 
6204  * Returns: %TRUE if the @file's contents were successfully loaded.
6205  * %FALSE if there were errors.
6206  **/
6207 gboolean
6208 g_file_load_contents (GFile         *file,
6209                       GCancellable  *cancellable,
6210                       char         **contents,
6211                       gsize         *length,
6212                       char         **etag_out,
6213                       GError       **error)
6214 {
6215   GFileInputStream *in;
6216   GByteArray *content;
6217   gsize pos;
6218   gssize res;
6219   GFileInfo *info;
6220
6221   g_return_val_if_fail (G_IS_FILE (file), FALSE);
6222   g_return_val_if_fail (contents != NULL, FALSE);
6223
6224   in = g_file_read (file, cancellable, error);
6225   if (in == NULL)
6226     return FALSE;
6227
6228   content = g_byte_array_new ();
6229   pos = 0;
6230   
6231   g_byte_array_set_size (content, pos + GET_CONTENT_BLOCK_SIZE + 1);
6232   while ((res = g_input_stream_read (G_INPUT_STREAM (in),
6233                                      content->data + pos,
6234                                      GET_CONTENT_BLOCK_SIZE,
6235                                      cancellable, error)) > 0)
6236     {
6237       pos += res;
6238       g_byte_array_set_size (content, pos + GET_CONTENT_BLOCK_SIZE + 1);
6239     }
6240
6241   if (etag_out)
6242     {
6243       *etag_out = NULL;
6244       
6245       info = g_file_input_stream_query_info (in,
6246                                              G_FILE_ATTRIBUTE_ETAG_VALUE,
6247                                              cancellable,
6248                                              NULL);
6249       if (info)
6250         {
6251           *etag_out = g_strdup (g_file_info_get_etag (info));
6252           g_object_unref (info);
6253         }
6254     } 
6255
6256   /* Ignore errors on close */
6257   g_input_stream_close (G_INPUT_STREAM (in), cancellable, NULL);
6258   g_object_unref (in);
6259
6260   if (res < 0)
6261     {
6262       /* error is set already */
6263       g_byte_array_free (content, TRUE);
6264       return FALSE;
6265     }
6266
6267   if (length)
6268     *length = pos;
6269
6270   /* Zero terminate (we got an extra byte allocated for this */
6271   content->data[pos] = 0;
6272   
6273   *contents = (char *)g_byte_array_free (content, FALSE);
6274   
6275   return TRUE;
6276 }
6277
6278 typedef struct {
6279   GFile *file;
6280   GError *error;
6281   GCancellable *cancellable;
6282   GFileReadMoreCallback read_more_callback;
6283   GAsyncReadyCallback callback;
6284   gpointer user_data;
6285   GByteArray *content;
6286   gsize pos;
6287   char *etag;
6288 } LoadContentsData;
6289
6290
6291 static void
6292 load_contents_data_free (LoadContentsData *data)
6293 {
6294   if (data->error)
6295     g_error_free (data->error);
6296   if (data->cancellable)
6297     g_object_unref (data->cancellable);
6298   if (data->content)
6299     g_byte_array_free (data->content, TRUE);
6300   g_free (data->etag);
6301   g_object_unref (data->file);
6302   g_free (data);
6303 }
6304
6305 static void
6306 load_contents_close_callback (GObject      *obj,
6307                               GAsyncResult *close_res,
6308                               gpointer      user_data)
6309 {
6310   GInputStream *stream = G_INPUT_STREAM (obj);
6311   LoadContentsData *data = user_data;
6312   GSimpleAsyncResult *res;
6313
6314   /* Ignore errors here, we're only reading anyway */
6315   g_input_stream_close_finish (stream, close_res, NULL);
6316   g_object_unref (stream);
6317
6318   res = g_simple_async_result_new (G_OBJECT (data->file),
6319                                    data->callback,
6320                                    data->user_data,
6321                                    g_file_load_contents_async);
6322   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)load_contents_data_free);
6323   g_simple_async_result_complete (res);
6324   g_object_unref (res);
6325 }
6326
6327 static void
6328 load_contents_fstat_callback (GObject      *obj,
6329                               GAsyncResult *stat_res,
6330                               gpointer      user_data)
6331 {
6332   GInputStream *stream = G_INPUT_STREAM (obj);
6333   LoadContentsData *data = user_data;
6334   GFileInfo *info;
6335
6336   info = g_file_input_stream_query_info_finish (G_FILE_INPUT_STREAM (stream),
6337                                                    stat_res, NULL);
6338   if (info)
6339     {
6340       data->etag = g_strdup (g_file_info_get_etag (info));
6341       g_object_unref (info);
6342     }
6343
6344   g_input_stream_close_async (stream, 0,
6345                               data->cancellable,
6346                               load_contents_close_callback, data);
6347 }
6348
6349 static void
6350 load_contents_read_callback (GObject      *obj,
6351                              GAsyncResult *read_res,
6352                              gpointer      user_data)
6353 {
6354   GInputStream *stream = G_INPUT_STREAM (obj);
6355   LoadContentsData *data = user_data;
6356   GError *error = NULL;
6357   gssize read_size;
6358
6359   read_size = g_input_stream_read_finish (stream, read_res, &error);
6360
6361   if (read_size < 0) 
6362     {
6363       /* Error or EOF, close the file */
6364       data->error = error;
6365       g_input_stream_close_async (stream, 0,
6366                                   data->cancellable,
6367                                   load_contents_close_callback, data);
6368     }
6369   else if (read_size == 0)
6370     {
6371       g_file_input_stream_query_info_async (G_FILE_INPUT_STREAM (stream),
6372                                             G_FILE_ATTRIBUTE_ETAG_VALUE,
6373                                             0,
6374                                             data->cancellable,
6375                                             load_contents_fstat_callback,
6376                                             data);
6377     }
6378   else if (read_size > 0)
6379     {
6380       data->pos += read_size;
6381       
6382       g_byte_array_set_size (data->content,
6383                              data->pos + GET_CONTENT_BLOCK_SIZE);
6384
6385
6386       if (data->read_more_callback &&
6387           !data->read_more_callback ((char *)data->content->data, data->pos, data->user_data))
6388         g_file_input_stream_query_info_async (G_FILE_INPUT_STREAM (stream),
6389                                               G_FILE_ATTRIBUTE_ETAG_VALUE,
6390                                               0,
6391                                               data->cancellable,
6392                                               load_contents_fstat_callback,
6393                                               data);
6394       else 
6395         g_input_stream_read_async (stream,
6396                                    data->content->data + data->pos,
6397                                    GET_CONTENT_BLOCK_SIZE,
6398                                    0,
6399                                    data->cancellable,
6400                                    load_contents_read_callback,
6401                                    data);
6402     }
6403 }
6404
6405 static void
6406 load_contents_open_callback (GObject      *obj,
6407                              GAsyncResult *open_res,
6408                              gpointer      user_data)
6409 {
6410   GFile *file = G_FILE (obj);
6411   GFileInputStream *stream;
6412   LoadContentsData *data = user_data;
6413   GError *error = NULL;
6414   GSimpleAsyncResult *res;
6415
6416   stream = g_file_read_finish (file, open_res, &error);
6417
6418   if (stream)
6419     {
6420       g_byte_array_set_size (data->content,
6421                              data->pos + GET_CONTENT_BLOCK_SIZE);
6422       g_input_stream_read_async (G_INPUT_STREAM (stream),
6423                                  data->content->data + data->pos,
6424                                  GET_CONTENT_BLOCK_SIZE,
6425                                  0,
6426                                  data->cancellable,
6427                                  load_contents_read_callback,
6428                                  data);
6429       
6430     }
6431   else
6432     {
6433       res = g_simple_async_result_new_take_error (G_OBJECT (data->file),
6434                                                   data->callback,
6435                                                   data->user_data,
6436                                                   error);
6437       g_simple_async_result_complete (res);
6438       load_contents_data_free (data);
6439       g_object_unref (res);
6440     }
6441 }
6442
6443 /**
6444  * g_file_load_partial_contents_async: (skip)
6445  * @file: input #GFile.
6446  * @cancellable: optional #GCancellable object, %NULL to ignore.
6447  * @read_more_callback: a #GFileReadMoreCallback to receive partial data and to specify whether further data should be read.
6448  * @callback: a #GAsyncReadyCallback to call when the request is satisfied
6449  * @user_data: the data to pass to the callback functions.
6450  *
6451  * Reads the partial contents of a file. A #GFileReadMoreCallback should be 
6452  * used to stop reading from the file when appropriate, else this function
6453  * will behave exactly as g_file_load_contents_async(). This operation 
6454  * can be finished by g_file_load_partial_contents_finish().
6455  *
6456  * Users of this function should be aware that @user_data is passed to 
6457  * both the @read_more_callback and the @callback.
6458  *
6459  * If @cancellable is not %NULL, then the operation can be cancelled by
6460  * triggering the cancellable object from another thread. If the operation
6461  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
6462  **/
6463 void
6464 g_file_load_partial_contents_async (GFile                 *file,
6465                                     GCancellable          *cancellable,
6466                                     GFileReadMoreCallback  read_more_callback,
6467                                     GAsyncReadyCallback    callback,
6468                                     gpointer               user_data)
6469 {
6470   LoadContentsData *data;
6471
6472   g_return_if_fail (G_IS_FILE (file));
6473
6474   data = g_new0 (LoadContentsData, 1);
6475
6476   if (cancellable)
6477     data->cancellable = g_object_ref (cancellable);
6478   data->read_more_callback = read_more_callback;
6479   data->callback = callback;
6480   data->user_data = user_data;
6481   data->content = g_byte_array_new ();
6482   data->file = g_object_ref (file);
6483
6484   g_file_read_async (file,
6485                      0,
6486                      cancellable,
6487                      load_contents_open_callback,
6488                      data);
6489 }
6490
6491 /**
6492  * g_file_load_partial_contents_finish:
6493  * @file: input #GFile.
6494  * @res: a #GAsyncResult. 
6495  * @contents: (out) (transfer full) (element-type guint8) (array length=length): a location to place the contents of the file.
6496  * @length: (out) (allow-none): a location to place the length of the contents of the file,
6497  *     or %NULL if the length is not needed
6498  * @etag_out: (out) (allow-none): a location to place the current entity tag for the file,
6499  *     or %NULL if the entity tag is not needed
6500  * @error: a #GError, or %NULL
6501  * 
6502  * Finishes an asynchronous partial load operation that was started
6503  * with g_file_load_partial_contents_async(). The data is always 
6504  * zero-terminated, but this is not included in the resultant @length.
6505  * The returned @content should be freed with g_free() when no longer
6506  * needed.
6507  *
6508  * Returns: %TRUE if the load was successful. If %FALSE and @error is 
6509  * present, it will be set appropriately. 
6510  **/
6511 gboolean
6512 g_file_load_partial_contents_finish (GFile         *file,
6513                                      GAsyncResult  *res,
6514                                      char         **contents,
6515                                      gsize         *length,
6516                                      char         **etag_out,
6517                                      GError       **error)
6518 {
6519   GSimpleAsyncResult *simple;
6520   LoadContentsData *data;
6521
6522   g_return_val_if_fail (G_IS_FILE (file), FALSE);
6523   g_return_val_if_fail (G_IS_SIMPLE_ASYNC_RESULT (res), FALSE);
6524   g_return_val_if_fail (contents != NULL, FALSE);
6525
6526   simple = G_SIMPLE_ASYNC_RESULT (res);
6527
6528   if (g_simple_async_result_propagate_error (simple, error))
6529     return FALSE;
6530   
6531   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_load_contents_async);
6532   
6533   data = g_simple_async_result_get_op_res_gpointer (simple);
6534
6535   if (data->error)
6536     {
6537       g_propagate_error (error, data->error);
6538       data->error = NULL;
6539       *contents = NULL;
6540       if (length)
6541         *length = 0;
6542       return FALSE;
6543     }
6544
6545   if (length)
6546     *length = data->pos;
6547
6548   if (etag_out)
6549     {
6550       *etag_out = data->etag;
6551       data->etag = NULL;
6552     }
6553
6554   /* Zero terminate */
6555   g_byte_array_set_size (data->content, data->pos + 1);
6556   data->content->data[data->pos] = 0;
6557   
6558   *contents = (char *)g_byte_array_free (data->content, FALSE);
6559   data->content = NULL;
6560
6561   return TRUE;
6562 }
6563
6564 /**
6565  * g_file_load_contents_async:
6566  * @file: input #GFile.
6567  * @cancellable: optional #GCancellable object, %NULL to ignore.
6568  * @callback: a #GAsyncReadyCallback to call when the request is satisfied
6569  * @user_data: the data to pass to callback function
6570  * 
6571  * Starts an asynchronous load of the @file's contents.
6572  *
6573  * For more details, see g_file_load_contents() which is
6574  * the synchronous version of this call.
6575  *
6576  * When the load operation has completed, @callback will be called 
6577  * with @user data. To finish the operation, call 
6578  * g_file_load_contents_finish() with the #GAsyncResult returned by 
6579  * the @callback.
6580  * 
6581  * If @cancellable is not %NULL, then the operation can be cancelled by
6582  * triggering the cancellable object from another thread. If the operation
6583  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
6584  **/
6585 void
6586 g_file_load_contents_async (GFile               *file,
6587                            GCancellable        *cancellable,
6588                            GAsyncReadyCallback  callback,
6589                            gpointer             user_data)
6590 {
6591   g_file_load_partial_contents_async (file,
6592                                       cancellable,
6593                                       NULL,
6594                                       callback, user_data);
6595 }
6596
6597 /**
6598  * g_file_load_contents_finish:
6599  * @file: input #GFile.
6600  * @res: a #GAsyncResult. 
6601  * @contents: (out) (transfer full) (element-type guint8) (array length=length): a location to place the contents of the file.
6602  * @length: (out) (allow-none): a location to place the length of the contents of the file,
6603  *     or %NULL if the length is not needed
6604  * @etag_out: (out) (allow-none): a location to place the current entity tag for the file,
6605  *     or %NULL if the entity tag is not needed
6606  * @error: a #GError, or %NULL
6607  * 
6608  * Finishes an asynchronous load of the @file's contents. 
6609  * The contents are placed in @contents, and @length is set to the 
6610  * size of the @contents string. The @content should be freed with
6611  * g_free() when no longer needed. If @etag_out is present, it will be 
6612  * set to the new entity tag for the @file.
6613  * 
6614  * Returns: %TRUE if the load was successful. If %FALSE and @error is 
6615  * present, it will be set appropriately. 
6616  **/
6617 gboolean
6618 g_file_load_contents_finish (GFile         *file,
6619                              GAsyncResult  *res,
6620                              char         **contents,
6621                              gsize         *length,
6622                              char         **etag_out,
6623                              GError       **error)
6624 {
6625   return g_file_load_partial_contents_finish (file,
6626                                               res,
6627                                               contents,
6628                                               length,
6629                                               etag_out,
6630                                               error);
6631 }
6632   
6633 /**
6634  * g_file_replace_contents:
6635  * @file: input #GFile.
6636  * @contents: (element-type guint8) (array length=length): a string containing the new contents for @file.
6637  * @length: the length of @contents in bytes.
6638  * @etag: (allow-none): the old <link linkend="gfile-etag">entity tag</link> 
6639  *     for the document, or %NULL
6640  * @make_backup: %TRUE if a backup should be created.
6641  * @flags: a set of #GFileCreateFlags.
6642  * @new_etag: (allow-none) (out): a location to a new <link linkend="gfile-etag">entity tag</link>
6643  *      for the document. This should be freed with g_free() when no longer 
6644  *      needed, or %NULL
6645  * @cancellable: optional #GCancellable object, %NULL to ignore.
6646  * @error: a #GError, or %NULL
6647  *
6648  * Replaces the contents of @file with @contents of @length bytes.
6649  
6650  * If @etag is specified (not %NULL) any existing file must have that etag, or
6651  * the error %G_IO_ERROR_WRONG_ETAG will be returned.
6652  *
6653  * If @make_backup is %TRUE, this function will attempt to make a backup of @file.
6654  * 
6655  * If @cancellable is not %NULL, then the operation can be cancelled by
6656  * triggering the cancellable object from another thread. If the operation
6657  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
6658  *
6659  * The returned @new_etag can be used to verify that the file hasn't changed the
6660  * next time it is saved over.
6661  * 
6662  * Returns: %TRUE if successful. If an error
6663  * has occurred, this function will return %FALSE and set @error
6664  * appropriately if present.
6665  **/
6666 gboolean
6667 g_file_replace_contents (GFile             *file,
6668                          const char        *contents,
6669                          gsize              length,
6670                          const char        *etag,
6671                          gboolean           make_backup,
6672                          GFileCreateFlags   flags,
6673                          char             **new_etag,
6674                          GCancellable      *cancellable,
6675                          GError           **error)
6676 {
6677   GFileOutputStream *out;
6678   gsize pos, remainder;
6679   gssize res;
6680   gboolean ret;
6681
6682   g_return_val_if_fail (G_IS_FILE (file), FALSE);
6683   g_return_val_if_fail (contents != NULL, FALSE);
6684
6685   out = g_file_replace (file, etag, make_backup, flags, cancellable, error);
6686   if (out == NULL)
6687     return FALSE;
6688
6689   pos = 0;
6690   remainder = length;
6691   while (remainder > 0 &&
6692          (res = g_output_stream_write (G_OUTPUT_STREAM (out),
6693                                        contents + pos,
6694                                        MIN (remainder, GET_CONTENT_BLOCK_SIZE),
6695                                        cancellable,
6696                                        error)) > 0)
6697     {
6698       pos += res;
6699       remainder -= res;
6700     }
6701   
6702   if (remainder > 0 && res < 0)
6703     {
6704       /* Ignore errors on close */
6705       g_output_stream_close (G_OUTPUT_STREAM (out), cancellable, NULL);
6706       g_object_unref (out);
6707
6708       /* error is set already */
6709       return FALSE;
6710     }
6711   
6712   ret = g_output_stream_close (G_OUTPUT_STREAM (out), cancellable, error);
6713
6714   if (new_etag)
6715     *new_etag = g_file_output_stream_get_etag (out);
6716
6717   g_object_unref (out);
6718
6719   return ret;
6720 }
6721
6722 typedef struct {
6723   GFile *file;
6724   GError *error;
6725   GCancellable *cancellable;
6726   GAsyncReadyCallback callback;
6727   gpointer user_data;
6728   const char *content;
6729   gsize length;
6730   gsize pos;
6731   char *etag;
6732 } ReplaceContentsData;
6733
6734 static void
6735 replace_contents_data_free (ReplaceContentsData *data)
6736 {
6737   if (data->error)
6738     g_error_free (data->error);
6739   if (data->cancellable)
6740     g_object_unref (data->cancellable);
6741   g_object_unref (data->file);
6742   g_free (data->etag);
6743   g_free (data);
6744 }
6745
6746 static void
6747 replace_contents_close_callback (GObject      *obj,
6748                                  GAsyncResult *close_res,
6749                                  gpointer      user_data)
6750 {
6751   GOutputStream *stream = G_OUTPUT_STREAM (obj);
6752   ReplaceContentsData *data = user_data;
6753   GSimpleAsyncResult *res;
6754
6755   /* Ignore errors here, we're only reading anyway */
6756   g_output_stream_close_finish (stream, close_res, NULL);
6757   g_object_unref (stream);
6758
6759   data->etag = g_file_output_stream_get_etag (G_FILE_OUTPUT_STREAM (stream));
6760   
6761   res = g_simple_async_result_new (G_OBJECT (data->file),
6762                                    data->callback,
6763                                    data->user_data,
6764                                    g_file_replace_contents_async);
6765   g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)replace_contents_data_free);
6766   g_simple_async_result_complete (res);
6767   g_object_unref (res);
6768 }
6769
6770 static void
6771 replace_contents_write_callback (GObject      *obj,
6772                                  GAsyncResult *read_res,
6773                                  gpointer      user_data)
6774 {
6775   GOutputStream *stream = G_OUTPUT_STREAM (obj);
6776   ReplaceContentsData *data = user_data;
6777   GError *error = NULL;
6778   gssize write_size;
6779   
6780   write_size = g_output_stream_write_finish (stream, read_res, &error);
6781
6782   if (write_size <= 0) 
6783     {
6784       /* Error or EOF, close the file */
6785       if (write_size < 0)
6786         data->error = error;
6787       g_output_stream_close_async (stream, 0,
6788                                    data->cancellable,
6789                                    replace_contents_close_callback, data);
6790     }
6791   else if (write_size > 0)
6792     {
6793       data->pos += write_size;
6794
6795       if (data->pos >= data->length)
6796         g_output_stream_close_async (stream, 0,
6797                                      data->cancellable,
6798                                      replace_contents_close_callback, data);
6799       else
6800         g_output_stream_write_async (stream,
6801                                      data->content + data->pos,
6802                                      data->length - data->pos,
6803                                      0,
6804                                      data->cancellable,
6805                                      replace_contents_write_callback,
6806                                      data);
6807     }
6808 }
6809
6810 static void
6811 replace_contents_open_callback (GObject      *obj,
6812                                 GAsyncResult *open_res,
6813                                 gpointer      user_data)
6814 {
6815   GFile *file = G_FILE (obj);
6816   GFileOutputStream *stream;
6817   ReplaceContentsData *data = user_data;
6818   GError *error = NULL;
6819   GSimpleAsyncResult *res;
6820
6821   stream = g_file_replace_finish (file, open_res, &error);
6822
6823   if (stream)
6824     {
6825       g_output_stream_write_async (G_OUTPUT_STREAM (stream),
6826                                    data->content + data->pos,
6827                                    data->length - data->pos,
6828                                    0,
6829                                    data->cancellable,
6830                                    replace_contents_write_callback,
6831                                    data);
6832       
6833     }
6834   else
6835     {
6836       res = g_simple_async_result_new_take_error (G_OBJECT (data->file),
6837                                                   data->callback,
6838                                                   data->user_data,
6839                                                   error);
6840       g_simple_async_result_complete (res);
6841       replace_contents_data_free (data);
6842       g_object_unref (res);
6843     }
6844 }
6845
6846 /**
6847  * g_file_replace_contents_async:
6848  * @file: input #GFile.
6849  * @contents: (element-type guint8) (array length=length): string of contents to replace the file with.
6850  * @length: the length of @contents in bytes.
6851  * @etag: (allow-none): a new <link linkend="gfile-etag">entity tag</link> for the @file, or %NULL
6852  * @make_backup: %TRUE if a backup should be created.
6853  * @flags: a set of #GFileCreateFlags.
6854  * @cancellable: optional #GCancellable object, %NULL to ignore.
6855  * @callback: a #GAsyncReadyCallback to call when the request is satisfied
6856  * @user_data: the data to pass to callback function
6857  * 
6858  * Starts an asynchronous replacement of @file with the given 
6859  * @contents of @length bytes. @etag will replace the document's 
6860  * current entity tag.
6861  * 
6862  * When this operation has completed, @callback will be called with
6863  * @user_user data, and the operation can be finalized with 
6864  * g_file_replace_contents_finish().
6865  * 
6866  * If @cancellable is not %NULL, then the operation can be cancelled by
6867  * triggering the cancellable object from another thread. If the operation
6868  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned. 
6869  * 
6870  * If @make_backup is %TRUE, this function will attempt to 
6871  * make a backup of @file.
6872  **/
6873 void
6874 g_file_replace_contents_async  (GFile               *file,
6875                                 const char          *contents,
6876                                 gsize                length,
6877                                 const char          *etag,
6878                                 gboolean             make_backup,
6879                                 GFileCreateFlags     flags,
6880                                 GCancellable        *cancellable,
6881                                 GAsyncReadyCallback  callback,
6882                                 gpointer             user_data)
6883 {
6884   ReplaceContentsData *data;
6885
6886   g_return_if_fail (G_IS_FILE (file));
6887   g_return_if_fail (contents != NULL);
6888
6889   data = g_new0 (ReplaceContentsData, 1);
6890
6891   if (cancellable)
6892     data->cancellable = g_object_ref (cancellable);
6893   data->callback = callback;
6894   data->user_data = user_data;
6895   data->content = contents;
6896   data->length = length;
6897   data->pos = 0;
6898   data->file = g_object_ref (file);
6899
6900   g_file_replace_async (file,
6901                         etag,
6902                         make_backup,
6903                         flags,
6904                         0,
6905                         cancellable,
6906                         replace_contents_open_callback,
6907                         data);
6908 }
6909   
6910 /**
6911  * g_file_replace_contents_finish:
6912  * @file: input #GFile.
6913  * @res: a #GAsyncResult. 
6914  * @new_etag: (out) (allow-none): a location of a new <link linkend="gfile-etag">entity tag</link> 
6915  *     for the document. This should be freed with g_free() when it is no 
6916  *     longer needed, or %NULL
6917  * @error: a #GError, or %NULL 
6918  * 
6919  * Finishes an asynchronous replace of the given @file. See
6920  * g_file_replace_contents_async(). Sets @new_etag to the new entity 
6921  * tag for the document, if present.
6922  * 
6923  * Returns: %TRUE on success, %FALSE on failure.
6924  **/
6925 gboolean
6926 g_file_replace_contents_finish (GFile         *file,
6927                                 GAsyncResult  *res,
6928                                 char         **new_etag,
6929                                 GError       **error)
6930 {
6931   GSimpleAsyncResult *simple;
6932   ReplaceContentsData *data;
6933
6934   g_return_val_if_fail (G_IS_FILE (file), FALSE);
6935   g_return_val_if_fail (G_IS_SIMPLE_ASYNC_RESULT (res), FALSE);
6936
6937   simple = G_SIMPLE_ASYNC_RESULT (res);
6938
6939   if (g_simple_async_result_propagate_error (simple, error))
6940     return FALSE;
6941   
6942   g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == g_file_replace_contents_async);
6943   
6944   data = g_simple_async_result_get_op_res_gpointer (simple);
6945
6946   if (data->error)
6947     {
6948       g_propagate_error (error, data->error);
6949       data->error = NULL;
6950       return FALSE;
6951     }
6952
6953
6954   if (new_etag)
6955     {
6956       *new_etag = data->etag;
6957       data->etag = NULL; /* Take ownership */
6958     }
6959   
6960   return TRUE;
6961 }
6962
6963 /**
6964  * g_file_start_mountable:
6965  * @file: input #GFile.
6966  * @flags: flags affecting the operation
6967  * @start_operation: a #GMountOperation, or %NULL to avoid user interaction.
6968  * @cancellable: optional #GCancellable object, %NULL to ignore.
6969  * @callback: a #GAsyncReadyCallback to call when the request is satisfied, or %NULL.
6970  * @user_data: the data to pass to callback function
6971  *
6972  * Starts a file of type G_FILE_TYPE_MOUNTABLE.
6973  * Using @start_operation, you can request callbacks when, for instance,
6974  * passwords are needed during authentication.
6975  *
6976  * If @cancellable is not %NULL, then the operation can be cancelled by
6977  * triggering the cancellable object from another thread. If the operation
6978  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
6979  *
6980  * When the operation is finished, @callback will be called. You can then call
6981  * g_file_mount_mountable_finish() to get the result of the operation.
6982  *
6983  * Since: 2.22
6984  */
6985 void
6986 g_file_start_mountable (GFile                      *file,
6987                         GDriveStartFlags            flags,
6988                         GMountOperation            *start_operation,
6989                         GCancellable               *cancellable,
6990                         GAsyncReadyCallback         callback,
6991                         gpointer                    user_data)
6992 {
6993   GFileIface *iface;
6994
6995   g_return_if_fail (G_IS_FILE (file));
6996
6997   iface = G_FILE_GET_IFACE (file);
6998
6999   if (iface->start_mountable == NULL)
7000     {
7001       g_simple_async_report_error_in_idle (G_OBJECT (file),
7002                                            callback,
7003                                            user_data,
7004                                            G_IO_ERROR,
7005                                            G_IO_ERROR_NOT_SUPPORTED,
7006                                            _("Operation not supported"));
7007       return;
7008     }
7009
7010   (* iface->start_mountable) (file,
7011                               flags,
7012                               start_operation,
7013                               cancellable,
7014                               callback,
7015                               user_data);
7016 }
7017
7018 /**
7019  * g_file_start_mountable_finish:
7020  * @file: input #GFile.
7021  * @result: a #GAsyncResult.
7022  * @error: a #GError, or %NULL
7023  *
7024  * Finishes a start operation. See g_file_start_mountable() for details.
7025  *
7026  * Finish an asynchronous start operation that was started
7027  * with g_file_start_mountable().
7028  *
7029  * Returns: %TRUE if the operation finished successfully. %FALSE
7030  * otherwise.
7031  *
7032  * Since: 2.22
7033  */
7034 gboolean
7035 g_file_start_mountable_finish (GFile                      *file,
7036                                GAsyncResult               *result,
7037                                GError                    **error)
7038 {
7039   GFileIface *iface;
7040
7041   g_return_val_if_fail (G_IS_FILE (file), FALSE);
7042   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), FALSE);
7043
7044   if (G_IS_SIMPLE_ASYNC_RESULT (result))
7045     {
7046       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
7047       if (g_simple_async_result_propagate_error (simple, error))
7048         return FALSE;
7049     }
7050
7051   iface = G_FILE_GET_IFACE (file);
7052   return (* iface->start_mountable_finish) (file, result, error);
7053 }
7054
7055 /**
7056  * g_file_stop_mountable:
7057  * @file: input #GFile.
7058  * @flags: flags affecting the operation
7059  * @mount_operation: a #GMountOperation, or %NULL to avoid user interaction.
7060  * @cancellable: optional #GCancellable object, %NULL to ignore.
7061  * @callback: a #GAsyncReadyCallback to call when the request is satisfied, or %NULL.
7062  * @user_data: the data to pass to callback function
7063  *
7064  * Stops a file of type G_FILE_TYPE_MOUNTABLE.
7065  *
7066  * If @cancellable is not %NULL, then the operation can be cancelled by
7067  * triggering the cancellable object from another thread. If the operation
7068  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
7069  *
7070  * When the operation is finished, @callback will be called. You can then call
7071  * g_file_stop_mountable_finish() to get the result of the operation.
7072  *
7073  * Since: 2.22
7074  */
7075 void
7076 g_file_stop_mountable (GFile                      *file,
7077                        GMountUnmountFlags          flags,
7078                        GMountOperation            *mount_operation,
7079                        GCancellable               *cancellable,
7080                        GAsyncReadyCallback         callback,
7081                        gpointer                    user_data)
7082 {
7083   GFileIface *iface;
7084
7085   g_return_if_fail (G_IS_FILE (file));
7086
7087   iface = G_FILE_GET_IFACE (file);
7088
7089   if (iface->stop_mountable == NULL)
7090     {
7091       g_simple_async_report_error_in_idle (G_OBJECT (file),
7092                                            callback,
7093                                            user_data,
7094                                            G_IO_ERROR,
7095                                            G_IO_ERROR_NOT_SUPPORTED,
7096                                            _("Operation not supported"));
7097       return;
7098     }
7099
7100   (* iface->stop_mountable) (file,
7101                              flags,
7102                              mount_operation,
7103                              cancellable,
7104                              callback,
7105                              user_data);
7106 }
7107
7108 /**
7109  * g_file_stop_mountable_finish:
7110  * @file: input #GFile.
7111  * @result: a #GAsyncResult.
7112  * @error: a #GError, or %NULL
7113  *
7114  * Finishes an stop operation, see g_file_stop_mountable() for details.
7115  *
7116  * Finish an asynchronous stop operation that was started
7117  * with g_file_stop_mountable().
7118  *
7119  * Returns: %TRUE if the operation finished successfully. %FALSE
7120  * otherwise.
7121  *
7122  * Since: 2.22
7123  */
7124 gboolean
7125 g_file_stop_mountable_finish (GFile                      *file,
7126                               GAsyncResult               *result,
7127                               GError                    **error)
7128 {
7129   GFileIface *iface;
7130
7131   g_return_val_if_fail (G_IS_FILE (file), FALSE);
7132   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), FALSE);
7133
7134   if (G_IS_SIMPLE_ASYNC_RESULT (result))
7135     {
7136       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
7137       if (g_simple_async_result_propagate_error (simple, error))
7138         return FALSE;
7139     }
7140
7141   iface = G_FILE_GET_IFACE (file);
7142   return (* iface->stop_mountable_finish) (file, result, error);
7143 }
7144
7145 /**
7146  * g_file_poll_mountable:
7147  * @file: input #GFile.
7148  * @cancellable: optional #GCancellable object, %NULL to ignore.
7149  * @callback: a #GAsyncReadyCallback to call when the request is satisfied, or %NULL.
7150  * @user_data: the data to pass to callback function
7151  *
7152  * Polls a file of type G_FILE_TYPE_MOUNTABLE.
7153  *
7154  * If @cancellable is not %NULL, then the operation can be cancelled by
7155  * triggering the cancellable object from another thread. If the operation
7156  * was cancelled, the error %G_IO_ERROR_CANCELLED will be returned.
7157  *
7158  * When the operation is finished, @callback will be called. You can then call
7159  * g_file_mount_mountable_finish() to get the result of the operation.
7160  *
7161  * Since: 2.22
7162  */
7163 void
7164 g_file_poll_mountable (GFile                      *file,
7165                        GCancellable               *cancellable,
7166                        GAsyncReadyCallback         callback,
7167                        gpointer                    user_data)
7168 {
7169   GFileIface *iface;
7170
7171   g_return_if_fail (G_IS_FILE (file));
7172
7173   iface = G_FILE_GET_IFACE (file);
7174
7175   if (iface->poll_mountable == NULL)
7176     {
7177       g_simple_async_report_error_in_idle (G_OBJECT (file),
7178                                            callback,
7179                                            user_data,
7180                                            G_IO_ERROR,
7181                                            G_IO_ERROR_NOT_SUPPORTED,
7182                                            _("Operation not supported"));
7183       return;
7184     }
7185
7186   (* iface->poll_mountable) (file,
7187                              cancellable,
7188                              callback,
7189                              user_data);
7190 }
7191
7192 /**
7193  * g_file_poll_mountable_finish:
7194  * @file: input #GFile.
7195  * @result: a #GAsyncResult.
7196  * @error: a #GError, or %NULL
7197  *
7198  * Finishes a poll operation. See g_file_poll_mountable() for details.
7199  *
7200  * Finish an asynchronous poll operation that was polled
7201  * with g_file_poll_mountable().
7202  *
7203  * Returns: %TRUE if the operation finished successfully. %FALSE
7204  * otherwise.
7205  *
7206  * Since: 2.22
7207  */
7208 gboolean
7209 g_file_poll_mountable_finish (GFile                      *file,
7210                               GAsyncResult               *result,
7211                               GError                    **error)
7212 {
7213   GFileIface *iface;
7214
7215   g_return_val_if_fail (G_IS_FILE (file), FALSE);
7216   g_return_val_if_fail (G_IS_ASYNC_RESULT (result), FALSE);
7217
7218   if (G_IS_SIMPLE_ASYNC_RESULT (result))
7219     {
7220       GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
7221       if (g_simple_async_result_propagate_error (simple, error))
7222         return FALSE;
7223     }
7224
7225   iface = G_FILE_GET_IFACE (file);
7226   return (* iface->poll_mountable_finish) (file, result, error);
7227 }
7228
7229 /**
7230  * g_file_supports_thread_contexts:
7231  * @file: a #GFile.
7232  *
7233  * Checks if @file supports <link
7234  * linkend="g-main-context-push-thread-default-context">thread-default
7235  * contexts</link>. If this returns %FALSE, you cannot perform
7236  * asynchronous operations on @file in a thread that has a
7237  * thread-default context.
7238  *
7239  * Returns: Whether or not @file supports thread-default contexts.
7240  *
7241  * Since: 2.22
7242  */
7243 gboolean
7244 g_file_supports_thread_contexts (GFile *file)
7245 {
7246  GFileIface *iface;
7247
7248  g_return_val_if_fail (G_IS_FILE (file), FALSE);
7249
7250  iface = G_FILE_GET_IFACE (file);
7251  return iface->supports_thread_contexts;
7252 }