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