summaryrefslogtreecommitdiffstats
path: root/xlators/protocol/client/src/client-handshake.c
diff options
context:
space:
mode:
Diffstat (limited to 'xlators/protocol/client/src/client-handshake.c')
-rw-r--r--xlators/protocol/client/src/client-handshake.c65
1 files changed, 44 insertions, 21 deletions
diff --git a/xlators/protocol/client/src/client-handshake.c b/xlators/protocol/client/src/client-handshake.c
index 7511813d3..8b0c90ebc 100644
--- a/xlators/protocol/client/src/client-handshake.c
+++ b/xlators/protocol/client/src/client-handshake.c
@@ -343,14 +343,38 @@ unwind:
}
int
+client_notify_parents_child_up (xlator_t *this)
+{
+ xlator_list_t *parent = NULL;
+
+ /* As fuse is not 'parent' of any translator now, triggering its
+ CHILD_UP event is hacky in case client has only client protocol */
+ if (!this->parents && this->ctx && this->ctx->master) {
+ /* send notify to 'ctx->master' if it exists */
+ xlator_notify (this->ctx->master, GF_EVENT_CHILD_UP,
+ this->graph);
+ }
+
+ parent = this->parents;
+ while (parent) {
+ xlator_notify (parent->xlator, GF_EVENT_CHILD_UP,
+ this);
+ parent = parent->next;
+ }
+
+ return 0;
+}
+
+int
client_post_handshake (call_frame_t *frame, xlator_t *this)
{
clnt_conf_t *conf = NULL;
clnt_fd_ctx_t *tmp = NULL;
clnt_fd_ctx_t *fdctx = NULL;
- xlator_list_t *parent = NULL;
struct list_head reopen_head;
+ int count = 0;
+
if (!this || !this->private)
goto out;
@@ -366,34 +390,33 @@ client_post_handshake (call_frame_t *frame, xlator_t *this)
list_del_init (&fdctx->sfd_pos);
list_add_tail (&fdctx->sfd_pos, &reopen_head);
+ count++;
}
}
pthread_mutex_unlock (&conf->lock);
- list_for_each_entry_safe (fdctx, tmp, &reopen_head, sfd_pos) {
- list_del_init (&fdctx->sfd_pos);
+ /* Delay notifying CHILD_UP to parents
+ until all locks are recovered */
+ if (count > 0) {
+ gf_log (this->name, GF_LOG_TRACE,
+ "%d fds open - Delaying child_up until they are re-opened",
+ count);
+ client_save_number_fds (conf, count);
- if (fdctx->is_dir)
- protocol_client_reopendir (this, fdctx);
- else
- protocol_client_reopen (this, fdctx);
- }
+ list_for_each_entry_safe (fdctx, tmp, &reopen_head, sfd_pos) {
+ list_del_init (&fdctx->sfd_pos);
- /* As fuse is not 'parent' of any translator now, triggering its
- CHILD_UP event is hacky in case client has only client protocol */
- if (!this->parents && this->ctx && this->ctx->master) {
- /* send notify to 'ctx->master' if it exists */
- xlator_notify (this->ctx->master, GF_EVENT_CHILD_UP,
- this->graph);
- }
+ if (fdctx->is_dir)
+ protocol_client_reopendir (this, fdctx);
+ else
+ protocol_client_reopen (this, fdctx);
+ }
+ } else {
+ gf_log (this->name, GF_LOG_TRACE,
+ "No open fds - notifying all parents child up");
+ client_notify_parents_child_up (this);
- parent = this->parents;
- while (parent) {
- xlator_notify (parent->xlator, GF_EVENT_CHILD_UP,
- this);
- parent = parent->next;
}
-
out:
return 0;
}