summaryrefslogtreecommitdiffstats
path: root/xlators
diff options
context:
space:
mode:
authorPranith Kumar K <pkarampu@redhat.com>2018-08-27 11:46:33 +0530
committerPranith Kumar K <pkarampu@redhat.com>2018-08-28 19:42:55 +0530
commitccaad48f51d4e8d3de001dc3907df68c69f8792b (patch)
tree817981603b393d9e60400ed83308ee0b10970778 /xlators
parent37f77b124283c3252ef00935628ff30b3e5696e6 (diff)
cluster/afr: Delegate metadata heal with pending xattrs to SHD
Problem: When metadata-self-heal is triggered on the mount, it blocks lookup until metadata-self-heal completes. But that can lead to hangs when lot of clients are accessing a directory which needs metadata heal and all of them trigger heals waiting for other clients to complete heal. Fix: Only when the heal is needed but the pending xattrs are not set, trigger metadata heal that could block lookup. This is the only case where different clients may give different metadata to the clients without heals, which should be avoided. Updates bz#1622821 Change-Id: I6089e9fda0770a83fb287941b229c882711f4e66 Signed-off-by: Pranith Kumar K <pkarampu@redhat.com>
Diffstat (limited to 'xlators')
-rw-r--r--xlators/cluster/afr/src/afr-common.c44
-rw-r--r--xlators/cluster/afr/src/afr-self-heal-common.c38
-rw-r--r--xlators/cluster/afr/src/afr.h3
3 files changed, 47 insertions, 38 deletions
diff --git a/xlators/cluster/afr/src/afr-common.c b/xlators/cluster/afr/src/afr-common.c
index 8b10e263974..cf55ebe1a63 100644
--- a/xlators/cluster/afr/src/afr-common.c
+++ b/xlators/cluster/afr/src/afr-common.c
@@ -2692,6 +2692,42 @@ out:
return 0;
}
+gf_boolean_t
+afr_is_pending_set (xlator_t *this, dict_t *xdata, int type)
+{
+ int idx = -1;
+ afr_private_t *priv = NULL;
+ void *pending_raw = NULL;
+ int *pending_int = NULL;
+ int i = 0;
+
+ priv = this->private;
+ idx = afr_index_for_transaction_type (type);
+
+ if (dict_get_ptr (xdata, AFR_DIRTY, &pending_raw) == 0) {
+ if (pending_raw) {
+ pending_int = pending_raw;
+
+ if (ntoh32 (pending_int[idx]))
+ return _gf_true;
+ }
+ }
+
+ for (i = 0; i < priv->child_count; i++) {
+ if (dict_get_ptr (xdata, priv->pending_key[i],
+ &pending_raw))
+ continue;
+ if (!pending_raw)
+ continue;
+ pending_int = pending_raw;
+
+ if (ntoh32 (pending_int[idx]))
+ return _gf_true;
+ }
+
+ return _gf_false;
+}
+
static gf_boolean_t
afr_can_start_metadata_self_heal(call_frame_t *frame, xlator_t *this)
{
@@ -2718,6 +2754,14 @@ afr_can_start_metadata_self_heal(call_frame_t *frame, xlator_t *this)
continue;
}
+ if (afr_is_pending_set (this, replies[i].xdata,
+ AFR_METADATA_TRANSACTION)) {
+ /* Let shd do the heal so that lookup is not blocked
+ * on getting metadata lock/doing the heal */
+ start = _gf_false;
+ break;
+ }
+
if (gf_uuid_compare (stbuf.ia_gfid, replies[i].poststat.ia_gfid)) {
start = _gf_false;
break;
diff --git a/xlators/cluster/afr/src/afr-self-heal-common.c b/xlators/cluster/afr/src/afr-self-heal-common.c
index 3cb69beabff..a1aad6315ac 100644
--- a/xlators/cluster/afr/src/afr-self-heal-common.c
+++ b/xlators/cluster/afr/src/afr-self-heal-common.c
@@ -2180,44 +2180,6 @@ afr_selfheal_unentrylk (call_frame_t *frame, xlator_t *this, inode_t *inode,
return 0;
}
-
-gf_boolean_t
-afr_is_pending_set (xlator_t *this, dict_t *xdata, int type)
-{
- int idx = -1;
- afr_private_t *priv = NULL;
- void *pending_raw = NULL;
- int *pending_int = NULL;
- int i = 0;
-
- priv = this->private;
- idx = afr_index_for_transaction_type (type);
-
- if (dict_get_ptr (xdata, AFR_DIRTY, &pending_raw) == 0) {
- if (pending_raw) {
- pending_int = pending_raw;
-
- if (ntoh32 (pending_int[idx]))
- return _gf_true;
- }
- }
-
- for (i = 0; i < priv->child_count; i++) {
- if (dict_get_ptr (xdata, priv->pending_key[i],
- &pending_raw))
- continue;
- if (!pending_raw)
- continue;
- pending_int = pending_raw;
-
- if (ntoh32 (pending_int[idx]))
- return _gf_true;
- }
-
- return _gf_false;
-}
-
-
gf_boolean_t
afr_is_data_set (xlator_t *this, dict_t *xdata)
{
diff --git a/xlators/cluster/afr/src/afr.h b/xlators/cluster/afr/src/afr.h
index d32ff5f8d85..155dc1d96af 100644
--- a/xlators/cluster/afr/src/afr.h
+++ b/xlators/cluster/afr/src/afr.h
@@ -1249,4 +1249,7 @@ afr_ta_post_op_lock (xlator_t *this, loc_t *loc);
int
afr_ta_post_op_unlock (xlator_t *this, loc_t *loc);
+
+gf_boolean_t
+afr_is_pending_set (xlator_t *this, dict_t *xdata, int type);
#endif /* __AFR_H__ */