From 430814992ddefae2588ae12e4d6aa4d66ed23461 Mon Sep 17 00:00:00 2001 From: Philip Withnall Date: Wed, 18 Feb 2015 17:01:18 +0000 Subject: [PATCH] docs: Expand introduction to mention using async calls over sync ones As discussed on the mailing list (see the whole thread): https://mail.gnome.org/archives/desktop-devel-list/2015-February/msg00126.html Expand the GIO documentation introduction to talk a little about when to use async and sync functions, and how the former should almost always be preferred over the latter. Link to this from the GFile documentation, which is an entry point for a lot of async calls. https://bugzilla.gnome.org/show_bug.cgi?id=744722 --- docs/reference/gio/overview.xml | 52 +++++++++++++++++++++++++++++++++++++++++ gio/gfile.c | 12 +++++++--- 2 files changed, 61 insertions(+), 3 deletions(-) diff --git a/docs/reference/gio/overview.xml b/docs/reference/gio/overview.xml index 46b49ca..78cc08c 100644 --- a/docs/reference/gio/overview.xml +++ b/docs/reference/gio/overview.xml @@ -190,6 +190,58 @@ + Asynchronous Programming + + + Many GIO functions come in two versions: synchronous and asynchronous, + denoted by an _async suffix. It is important to use these + appropriately: synchronous calls should not be used from + within a main loop which is shared with other code, such as one in the + application’s main thread. Synchronous calls block until they complete, + and I/O operations can take noticeable amounts of time (even on ‘fast’ + SSDs). Blocking a main loop iteration while waiting for I/O means that + other sources in the main loop will not be dispatched, such as input and + redraw handlers for the application’s UI. This can cause the application + to ‘freeze’ until I/O completes. + + + + A few self-contained groups of functions, such as code generated by + gdbus-codegen, + use a different convention: functions are asynchronous default, and it is + the synchronous version which has a + _sync + suffix. Aside from naming differences, they should be treated the same + way as functions following the normal convention above. + + + + The asynchronous (_async) versions of functions return + control to the caller immediately, after scheduling the I/O in the kernel + and adding a callback for it to the main loop. This callback will be + invoked when the operation has completed. From the callback, the paired + _finish function should be called to retrieve the return + value of the I/O operation, and any errors which occurred. For more + information on using and implementing asynchronous functions, see + GAsyncResult + and GTask. + + + + By starting multiple asynchronous operations in succession, they will be + executed in parallel (up to an arbitrary limit imposed by GIO’s internal + worker thread pool). + + + + The synchronous versions of functions can be used early in application + startup when there is no main loop to block, for example to load initial + configuration files. They can also be used for I/O on files which are + guaranteed to be small and on the local disk. Note that the user’s home + directory is not guaranteed to be on the local disk. + + + Security diff --git a/gio/gfile.c b/gio/gfile.c index 22f7423..8925215 100644 --- a/gio/gfile.c +++ b/gio/gfile.c @@ -126,9 +126,15 @@ * the operation, producing a GAsyncResult which is then passed to the * function's matching _finish() operation. * - * Some #GFile operations do not have synchronous analogs, as they may - * take a very long time to finish, and blocking may leave an application - * unusable. Notable cases include: + * It is highly recommended to use asynchronous calls when running within a + * shared main loop, such as in the main thread of an application. This avoids + * I/O operations blocking other sources on the main loop from being dispatched. + * Synchronous I/O operations should be performed from worker threads. See the + * [introduction to asynchronous programming section][async-programming] for + * more. + * + * Some #GFile operations almost always take a noticeable amount of time, and + * so do not have synchronous analogs. Notable cases include: * - g_file_mount_mountable() to mount a mountable file. * - g_file_unmount_mountable_with_operation() to unmount a mountable file. * - g_file_eject_mountable_with_operation() to eject a mountable file. -- 2.7.4