summaryrefslogtreecommitdiffstats
path: root/xlators/features/locks/src/common.c
diff options
context:
space:
mode:
Diffstat (limited to 'xlators/features/locks/src/common.c')
-rw-r--r--xlators/features/locks/src/common.c53
1 files changed, 52 insertions, 1 deletions
diff --git a/xlators/features/locks/src/common.c b/xlators/features/locks/src/common.c
index 08dc451e16e..b9037688a3f 100644
--- a/xlators/features/locks/src/common.c
+++ b/xlators/features/locks/src/common.c
@@ -35,6 +35,7 @@
#include "common-utils.h"
#include "locks.h"
+#include "common.h"
static int
@@ -43,7 +44,7 @@ static void
__insert_and_merge (pl_inode_t *pl_inode, posix_lock_t *lock);
static pl_dom_list_t *
-allocate_domain(const char *volume)
+allocate_domain (const char *volume)
{
pl_dom_list_t *dom = NULL;
@@ -95,6 +96,56 @@ found:
return dom;
}
+
+int
+__pl_inode_is_empty (pl_inode_t *pl_inode)
+{
+ pl_dom_list_t *dom = NULL;
+ int is_empty = 1;
+
+ if (!list_empty (&pl_inode->ext_list))
+ is_empty = 0;
+
+ list_for_each_entry (dom, &pl_inode->dom_list, inode_list) {
+ if (!list_empty (&dom->entrylk_list))
+ is_empty = 0;
+
+ if (!list_empty (&dom->inodelk_list))
+ is_empty = 0;
+ }
+
+ return is_empty;
+}
+
+void
+pl_update_refkeeper (xlator_t *this, inode_t *inode)
+{
+ pl_inode_t *pl_inode = NULL;
+ int is_empty = 0;
+ int need_unref = 0;
+
+ pl_inode = pl_inode_get (this, inode);
+
+ pthread_mutex_lock (&pl_inode->mutex);
+ {
+ is_empty = __pl_inode_is_empty (pl_inode);
+
+ if (is_empty && pl_inode->refkeeper) {
+ need_unref = 1;
+ pl_inode->refkeeper = NULL;
+ }
+
+ if (!is_empty && !pl_inode->refkeeper) {
+ pl_inode->refkeeper = inode_ref (inode);
+ }
+ }
+ pthread_mutex_unlock (&pl_inode->mutex);
+
+ if (need_unref)
+ inode_unref (inode);
+}
+
+
pl_inode_t *
pl_inode_get (xlator_t *this, inode_t *inode)
{