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