From 9ee330aaf0831bc04e2ed72c05be0701571b5294 Mon Sep 17 00:00:00 2001 From: Raghavendra Gowdappa Date: Thu, 6 Dec 2018 13:24:40 +0530 Subject: performance/readdir-ahead: update stats from prefetched dentries stats from prefetched dentries should be invalidated only if the files pointed to those dentries were written in the window of prefetching. Otherwise its safe to use these stats. Change-Id: I9ea5aeea4c75dfa03387fca32c626cb4e693290d Signed-off-by: Raghavendra Gowdappa Fixes: bz#1656348 --- .../performance/readdir-ahead/src/readdir-ahead.c | 97 ++++++++++++++++++++-- .../performance/readdir-ahead/src/readdir-ahead.h | 2 + 2 files changed, 93 insertions(+), 6 deletions(-) (limited to 'xlators') diff --git a/xlators/performance/readdir-ahead/src/readdir-ahead.c b/xlators/performance/readdir-ahead/src/readdir-ahead.c index dee977c6e21..2d2c807ccd6 100644 --- a/xlators/performance/readdir-ahead/src/readdir-ahead.c +++ b/xlators/performance/readdir-ahead/src/readdir-ahead.c @@ -145,7 +145,8 @@ __rda_inode_ctx_update_iatts(inode_t *inode, xlator_t *this, goto out; } } else { - if (generation != GF_ATOMIC_GET(ctx_p->generation)) + if ((generation != -1) && + (generation != GF_ATOMIC_GET(ctx_p->generation))) goto out; } @@ -201,6 +202,60 @@ rda_reset_ctx(xlator_t *this, struct rda_fd_ctx *ctx) } } +static void +rda_mark_inode_dirty(xlator_t *this, inode_t *inode) +{ + inode_t *parent = NULL; + fd_t *fd = NULL; + uint64_t val = 0; + int32_t ret = 0; + struct rda_fd_ctx *fd_ctx = NULL; + char gfid[GF_UUID_BUF_SIZE] = {0}; + + parent = inode_parent(inode, NULL, NULL); + if (parent) { + LOCK(&parent->lock); + { + list_for_each_entry(fd, &parent->fd_list, inode_list) + { + val = 0; + fd_ctx_get(fd, this, &val); + if (val == 0) + continue; + + fd_ctx = (void *)val; + uuid_utoa_r(inode->gfid, gfid); + if (!GF_ATOMIC_GET(fd_ctx->prefetching)) + continue; + + LOCK(&fd_ctx->lock); + { + if (GF_ATOMIC_GET(fd_ctx->prefetching)) { + if (fd_ctx->writes_during_prefetch == NULL) + fd_ctx->writes_during_prefetch = dict_new(); + + ret = dict_set_int8(fd_ctx->writes_during_prefetch, + gfid, 1); + if (ret < 0) { + gf_log(this->name, GF_LOG_WARNING, + "marking to invalidate stats of %s from an " + "in progress " + "prefetching has failed, might result in " + "stale stat to " + "application", + gfid); + } + } + } + UNLOCK(&fd_ctx->lock); + } + } + UNLOCK(&parent->lock); + } + + return; +} + /* * Check whether we can handle a request. Offset verification is done by the * caller, so we only check whether the preload buffer has completion status @@ -433,6 +488,10 @@ rda_fill_fd_cbk(call_frame_t *frame, void *cookie, xlator_t *this, int ret = 0; gf_boolean_t serve = _gf_false; call_stub_t *stub = NULL; + char gfid[GF_UUID_BUF_SIZE] = { + 0, + }; + uint64_t generation = 0; INIT_LIST_HEAD(&serve_entries.list); LOCK(&ctx->lock); @@ -460,8 +519,16 @@ rda_fill_fd_cbk(call_frame_t *frame, void *cookie, xlator_t *this, * request was initiated. So, we pass 0 for * generation number */ + generation = -1; + if (ctx->writes_during_prefetch) { + memset(gfid, 0, sizeof(gfid)); + uuid_utoa_r(dirent->inode->gfid, gfid); + if (dict_get(ctx->writes_during_prefetch, gfid)) + generation = 0; + } + rda_inode_ctx_update_iatts(dirent->inode, this, &dirent->d_stat, - &dirent->d_stat, 0); + &dirent->d_stat, generation); } dirent_size = gf_dirent_size(dirent->d_name); @@ -474,6 +541,13 @@ rda_fill_fd_cbk(call_frame_t *frame, void *cookie, xlator_t *this, } } + if (ctx->writes_during_prefetch) { + dict_unref(ctx->writes_during_prefetch); + ctx->writes_during_prefetch = NULL; + } + + GF_ATOMIC_DEC(ctx->prefetching); + if (ctx->cur_size >= priv->rda_high_wmark) ctx->state &= ~RDA_FD_PLUGGED; @@ -603,6 +677,7 @@ rda_fill_fd(call_frame_t *frame, xlator_t *this, fd_t *fd) } local->offset = offset; + GF_ATOMIC_INC(ctx->prefetching); UNLOCK(&ctx->lock); @@ -685,6 +760,9 @@ rda_writev_cbk(call_frame_t *frame, void *cookie, xlator_t *this, goto unwind; local = frame->local; + + rda_mark_inode_dirty(this, local->inode); + rda_inode_ctx_update_iatts(local->inode, this, postbuf, &postbuf_out, local->generation); @@ -720,6 +798,7 @@ rda_fallocate_cbk(call_frame_t *frame, void *cookie, xlator_t *this, goto unwind; local = frame->local; + rda_mark_inode_dirty(this, local->inode); rda_inode_ctx_update_iatts(local->inode, this, postbuf, &postbuf_out, local->generation); @@ -755,6 +834,7 @@ rda_zerofill_cbk(call_frame_t *frame, void *cookie, xlator_t *this, goto unwind; local = frame->local; + rda_mark_inode_dirty(this, local->inode); rda_inode_ctx_update_iatts(local->inode, this, postbuf, &postbuf_out, local->generation); @@ -790,6 +870,7 @@ rda_discard_cbk(call_frame_t *frame, void *cookie, xlator_t *this, goto unwind; local = frame->local; + rda_mark_inode_dirty(this, local->inode); rda_inode_ctx_update_iatts(local->inode, this, postbuf, &postbuf_out, local->generation); @@ -824,6 +905,7 @@ rda_ftruncate_cbk(call_frame_t *frame, void *cookie, xlator_t *this, goto unwind; local = frame->local; + rda_mark_inode_dirty(this, local->inode); rda_inode_ctx_update_iatts(local->inode, this, postbuf, &postbuf_out, local->generation); @@ -859,6 +941,7 @@ rda_truncate_cbk(call_frame_t *frame, void *cookie, xlator_t *this, goto unwind; local = frame->local; + rda_mark_inode_dirty(this, local->inode); rda_inode_ctx_update_iatts(local->inode, this, postbuf, &postbuf_out, local->generation); if (postbuf_out.ia_ctime == 0) @@ -889,7 +972,7 @@ rda_setxattr_cbk(call_frame_t *frame, void *cookie, xlator_t *this, goto unwind; local = frame->local; - + rda_mark_inode_dirty(this, local->inode); rda_inode_ctx_update_iatts(local->inode, this, NULL, NULL, local->generation); unwind: @@ -916,7 +999,7 @@ rda_fsetxattr_cbk(call_frame_t *frame, void *cookie, xlator_t *this, goto unwind; local = frame->local; - + rda_mark_inode_dirty(this, local->inode); rda_inode_ctx_update_iatts(local->inode, this, NULL, NULL, local->generation); unwind: @@ -947,6 +1030,7 @@ rda_setattr_cbk(call_frame_t *frame, void *cookie, xlator_t *this, goto unwind; local = frame->local; + rda_mark_inode_dirty(this, local->inode); rda_inode_ctx_update_iatts(local->inode, this, statpost, &postbuf_out, local->generation); if (postbuf_out.ia_ctime == 0) @@ -981,6 +1065,7 @@ rda_fsetattr_cbk(call_frame_t *frame, void *cookie, xlator_t *this, goto unwind; local = frame->local; + rda_mark_inode_dirty(this, local->inode); rda_inode_ctx_update_iatts(local->inode, this, statpost, &postbuf_out, local->generation); if (postbuf_out.ia_ctime == 0) @@ -1011,7 +1096,7 @@ rda_removexattr_cbk(call_frame_t *frame, void *cookie, xlator_t *this, goto unwind; local = frame->local; - + rda_mark_inode_dirty(this, local->inode); rda_inode_ctx_update_iatts(local->inode, this, NULL, NULL, local->generation); unwind: @@ -1038,7 +1123,7 @@ rda_fremovexattr_cbk(call_frame_t *frame, void *cookie, xlator_t *this, goto unwind; local = frame->local; - + rda_mark_inode_dirty(this, local->inode); rda_inode_ctx_update_iatts(local->inode, this, NULL, NULL, local->generation); unwind: diff --git a/xlators/performance/readdir-ahead/src/readdir-ahead.h b/xlators/performance/readdir-ahead/src/readdir-ahead.h index b5e13800826..619c41059ff 100644 --- a/xlators/performance/readdir-ahead/src/readdir-ahead.h +++ b/xlators/performance/readdir-ahead/src/readdir-ahead.h @@ -67,6 +67,8 @@ struct rda_fd_ctx { call_stub_t *stub; int op_errno; dict_t *xattrs; /* md-cache keys to be sent in readdirp() */ + dict_t *writes_during_prefetch; + gf_atomic_t prefetching; }; struct rda_local { -- cgit