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 <rgowdapp@redhat.com> Fixes: bz#1656348
This commit is contained in:
parent
40a9e53a44
commit
9ee330aaf0
@ -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:
|
||||
|
@ -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 {
|
||||
|
Loading…
x
Reference in New Issue
Block a user