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