lib/repo: Add locking auto cleanup handler
authorDan Nicholson <nicholson@endlessm.com>
Fri, 13 Oct 2017 19:31:35 +0000 (19:31 +0000)
committerAtomic Bot <atomic-devel@projectatomic.io>
Tue, 5 Dec 2017 02:32:47 +0000 (02:32 +0000)
Define an auto cleanup handler for use with repo locking. This is based
on the existing auto transaction cleanup. A wrapper for
ostree_repo_lock_push() is added with it. The intended usage is like so:

  g_autoptr(OstreeRepoAutoLock) lock = NULL;
  lock = ostree_repo_auto_lock_push (repo, lock_type, cancellable, error);
  if (!lock)
    return FALSE;

The functions and type are marked to be skipped by introspection since I
can't see them being usable from bindings.

Closes: #1343
Approved by: cgwalters

apidoc/ostree-experimental-sections.txt
src/libostree/libostree-experimental.sym
src/libostree/ostree-autocleanups.h
src/libostree/ostree-repo-private.h
src/libostree/ostree-repo.c
src/libostree/ostree-repo.h

index 61f43f286dca450e85eb1e198da5eb2d30319779..0d1684066929e8f32d9b1ad5604fc55e9f9589df 100644 (file)
@@ -93,6 +93,9 @@ ostree_repo_finder_override_get_type
 OstreeRepoLockType
 ostree_repo_lock_push
 ostree_repo_lock_pop
+OstreeRepoAutoLock
+ostree_repo_auto_lock_push
+ostree_repo_auto_lock_cleanup
 ostree_repo_get_collection_id
 ostree_repo_set_collection_id
 ostree_validate_collection_id
index 15730546113f99fb56822712427c4e38f8c2753c..3f3454f3bcd22b5ea4a86d869bb05a70909c9b6e 100644 (file)
@@ -94,6 +94,8 @@ LIBOSTREE_2017.14_EXPERIMENTAL {
 global:
   ostree_remote_get_type;
   ostree_remote_get_url;
+  ostree_repo_auto_lock_cleanup;
+  ostree_repo_auto_lock_push;
   ostree_repo_lock_pop;
   ostree_repo_lock_push;
 } LIBOSTREE_2017.13_EXPERIMENTAL;
index c8e8a8572dc73483fb9951edbd4c094e5b8b22e5..b3974317fa7e53ae6dcd31b6abbdcd7be31d0216 100644 (file)
@@ -59,6 +59,7 @@ G_DEFINE_AUTOPTR_CLEANUP_FUNC (OstreeSysrootUpgrader, g_object_unref)
 G_DEFINE_AUTO_CLEANUP_CLEAR_FUNC (OstreeRepoCommitTraverseIter, ostree_repo_commit_traverse_iter_clear)
 
 #ifdef OSTREE_ENABLE_EXPERIMENTAL_API
+G_DEFINE_AUTOPTR_CLEANUP_FUNC (OstreeRepoAutoLock, ostree_repo_auto_lock_cleanup)
 G_DEFINE_AUTOPTR_CLEANUP_FUNC (OstreeCollectionRef, ostree_collection_ref_free)
 G_DEFINE_AUTO_CLEANUP_FREE_FUNC (OstreeCollectionRefv, ostree_collection_ref_freev, NULL)
 G_DEFINE_AUTOPTR_CLEANUP_FUNC (OstreeRemote, ostree_remote_unref)
index 452b2b3594294eb3a0cb8e49564ccea73cdcf2bd..ae51cea342b3280bb3cdbf68a35e3b62fc301e1e 100644 (file)
@@ -456,6 +456,15 @@ gboolean      ostree_repo_lock_pop (OstreeRepo    *self,
                                     GCancellable  *cancellable,
                                     GError       **error);
 
+typedef OstreeRepo OstreeRepoAutoLock;
+
+OstreeRepoAutoLock * ostree_repo_auto_lock_push (OstreeRepo          *self,
+                                                 OstreeRepoLockType   lock_type,
+                                                 GCancellable        *cancellable,
+                                                 GError             **error);
+void          ostree_repo_auto_lock_cleanup (OstreeRepoAutoLock *lock);
+G_DEFINE_AUTOPTR_CLEANUP_FUNC (OstreeRepoAutoLock, ostree_repo_auto_lock_cleanup)
+
 const gchar * ostree_repo_get_collection_id (OstreeRepo   *self);
 gboolean      ostree_repo_set_collection_id (OstreeRepo   *self,
                                              const gchar  *collection_id,
index 9c2d5fb59eeb0882ee2eb3896c0e59d3f1a7069c..039f437b180a269fd1e5e49f3b3fd4380471b5c5 100644 (file)
@@ -612,6 +612,66 @@ ostree_repo_lock_pop (OstreeRepo    *self,
     }
 }
 
+/**
+ * ostree_repo_auto_lock_push: (skip)
+ * @self: a #OstreeRepo
+ * @lock_type: the type of lock to acquire
+ * @cancellable: a #GCancellable
+ * @error: a #GError
+ *
+ * Like ostree_repo_lock_push(), but for usage with #OstreeRepoAutoLock.
+ * The intended usage is to declare the #OstreeRepoAutoLock with
+ * g_autoptr() so that ostree_repo_auto_lock_cleanup() is called when it
+ * goes out of scope. This will automatically pop the lock status off
+ * the stack if it was acquired successfully.
+ *
+ * |[<!-- language="C" -->
+ * g_autoptr(OstreeRepoAutoLock) lock = NULL;
+ * lock = ostree_repo_auto_lock_push (repo, lock_type, cancellable, error);
+ * if (!lock)
+ *   return FALSE;
+ * ]|
+ *
+ * Returns: @self on success, otherwise %NULL with @error set
+ * Since: 2017.14
+ */
+OstreeRepoAutoLock *
+ostree_repo_auto_lock_push (OstreeRepo          *self,
+                            OstreeRepoLockType   lock_type,
+                            GCancellable        *cancellable,
+                            GError             **error)
+{
+  if (!ostree_repo_lock_push (self, lock_type, cancellable, error))
+    return NULL;
+  return (OstreeRepoAutoLock *)self;
+}
+
+/**
+ * ostree_repo_auto_lock_cleanup: (skip)
+ * @lock: a #OstreeRepoAutoLock
+ *
+ * A cleanup handler for use with ostree_repo_auto_lock_push(). If @lock is
+ * not %NULL, ostree_repo_lock_pop() will be called on it. If
+ * ostree_repo_lock_pop() fails, a critical warning will be emitted.
+ *
+ * Since: 2017.14
+ */
+void
+ostree_repo_auto_lock_cleanup (OstreeRepoAutoLock *lock)
+{
+  OstreeRepo *repo = lock;
+  if (repo)
+    {
+      g_autoptr(GError) error = NULL;
+      int errsv = errno;
+
+      if (!ostree_repo_lock_pop (repo, NULL, &error))
+        g_critical ("Cleanup repo lock failed: %s", error->message);
+
+      errno = errsv;
+    }
+}
+
 static GFile *
 get_remotes_d_dir (OstreeRepo          *self,
                    GFile               *sysroot);
index 13074582685c43d658118deb3ec3f1882385c9b1..7ce47a56534eecfb0767b58f6bc866336f95d941 100644 (file)
@@ -131,6 +131,24 @@ gboolean      ostree_repo_lock_pop (OstreeRepo    *self,
                                     GCancellable  *cancellable,
                                     GError       **error);
 
+/**
+ * OstreeRepoAutoLock: (skip)
+ *
+ * This is simply an alias to #OstreeRepo used for automatic lock cleanup.
+ * See ostree_repo_auto_lock_push() for its intended usage.
+ *
+ * Since: 2017.14
+ */
+typedef OstreeRepo OstreeRepoAutoLock;
+
+_OSTREE_PUBLIC
+OstreeRepoAutoLock * ostree_repo_auto_lock_push (OstreeRepo          *self,
+                                                 OstreeRepoLockType   lock_type,
+                                                 GCancellable        *cancellable,
+                                                 GError             **error);
+_OSTREE_PUBLIC
+void          ostree_repo_auto_lock_cleanup (OstreeRepoAutoLock *lock);
+
 _OSTREE_PUBLIC
 const gchar * ostree_repo_get_collection_id (OstreeRepo   *self);
 _OSTREE_PUBLIC