mirror of
https://mirrors.bfsu.edu.cn/git/linux.git
synced 2024-11-24 12:44:11 +08:00
ceph: request Fw caps before updating the mtime in ceph_write_iter
The current code will update the mtime and then try to get caps to handle the write. If we end up having to request caps from the MDS, then the mtime in the cap grant will clobber the updated mtime and it'll be lost. This is most noticable when two clients are alternately writing to the same file. Fw caps are continually being granted and revoked, and the mtime ends up stuck because the updated mtimes are always being overwritten with the old one. Fix this by changing the order of operations in ceph_write_iter to get the caps before updating the times. Also, make sure we check the pool full conditions before even getting any caps or uninlining. URL: https://tracker.ceph.com/issues/46574 Reported-by: Jozef Kováč <kovac@firma.zoznam.sk> Signed-off-by: Jeff Layton <jlayton@kernel.org> Reviewed-by: Xiubo Li <xiubli@redhat.com> Reviewed-by: Luis Henriques <lhenriques@suse.de> Signed-off-by: Ilya Dryomov <idryomov@gmail.com>
This commit is contained in:
parent
d517b3983d
commit
b11ed50346
@ -1722,22 +1722,6 @@ retry_snap:
|
||||
goto out;
|
||||
}
|
||||
|
||||
err = file_remove_privs(file);
|
||||
if (err)
|
||||
goto out;
|
||||
|
||||
err = file_update_time(file);
|
||||
if (err)
|
||||
goto out;
|
||||
|
||||
inode_inc_iversion_raw(inode);
|
||||
|
||||
if (ci->i_inline_version != CEPH_INLINE_NONE) {
|
||||
err = ceph_uninline_data(file, NULL);
|
||||
if (err < 0)
|
||||
goto out;
|
||||
}
|
||||
|
||||
down_read(&osdc->lock);
|
||||
map_flags = osdc->osdmap->flags;
|
||||
pool_flags = ceph_pg_pool_flags(osdc->osdmap, ci->i_layout.pool_id);
|
||||
@ -1748,6 +1732,16 @@ retry_snap:
|
||||
goto out;
|
||||
}
|
||||
|
||||
err = file_remove_privs(file);
|
||||
if (err)
|
||||
goto out;
|
||||
|
||||
if (ci->i_inline_version != CEPH_INLINE_NONE) {
|
||||
err = ceph_uninline_data(file, NULL);
|
||||
if (err < 0)
|
||||
goto out;
|
||||
}
|
||||
|
||||
dout("aio_write %p %llx.%llx %llu~%zd getting caps. i_size %llu\n",
|
||||
inode, ceph_vinop(inode), pos, count, i_size_read(inode));
|
||||
if (fi->fmode & CEPH_FILE_MODE_LAZY)
|
||||
@ -1759,6 +1753,12 @@ retry_snap:
|
||||
if (err < 0)
|
||||
goto out;
|
||||
|
||||
err = file_update_time(file);
|
||||
if (err)
|
||||
goto out_caps;
|
||||
|
||||
inode_inc_iversion_raw(inode);
|
||||
|
||||
dout("aio_write %p %llx.%llx %llu~%zd got cap refs on %s\n",
|
||||
inode, ceph_vinop(inode), pos, count, ceph_cap_string(got));
|
||||
|
||||
@ -1842,6 +1842,8 @@ retry_snap:
|
||||
}
|
||||
|
||||
goto out_unlocked;
|
||||
out_caps:
|
||||
ceph_put_cap_refs(ci, got);
|
||||
out:
|
||||
if (direct_lock)
|
||||
ceph_end_io_direct(inode);
|
||||
|
Loading…
Reference in New Issue
Block a user