From: "Darrick J. Wong" <darrick.wong@oracle.com> To: david@fromorbit.com, darrick.wong@oracle.com Cc: linux-xfs@vger.kernel.org, linux-fsdevel@vger.kernel.org, linux-btrfs@vger.kernel.org, ocfs2-devel@oss.oracle.com, sandeen@redhat.com Subject: [PATCH 14/15] ocfs2: support partial clone range and dedupe range Date: Thu, 04 Oct 2018 17:46:20 -0700 [thread overview] Message-ID: <153870038054.29072.6999468698657448422.stgit@magnolia> (raw) In-Reply-To: <153870027422.29072.7433543674436957232.stgit@magnolia> From: Darrick J. Wong <darrick.wong@oracle.com> Change the ocfs2 remap code to allow for returning partial results. Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com> --- fs/ocfs2/file.c | 14 ++++---------- fs/ocfs2/refcounttree.c | 35 ++++++++++++++++++++--------------- fs/ocfs2/refcounttree.h | 4 ++-- 3 files changed, 26 insertions(+), 27 deletions(-) diff --git a/fs/ocfs2/file.c b/fs/ocfs2/file.c index 1ee6d3ecdac6..4562111259b4 100644 --- a/fs/ocfs2/file.c +++ b/fs/ocfs2/file.c @@ -2534,11 +2534,8 @@ static s64 ocfs2_file_clone_range(struct file *file_in, u64 len, unsigned int flags) { - int ret; - - ret = ocfs2_reflink_remap_range(file_in, pos_in, file_out, pos_out, - len, false); - return ret < 0 ? ret : len; + return ocfs2_reflink_remap_range(file_in, pos_in, file_out, pos_out, + len, flags); } static s64 ocfs2_file_dedupe_range(struct file *file_in, @@ -2547,11 +2544,8 @@ static s64 ocfs2_file_dedupe_range(struct file *file_in, loff_t pos_out, u64 len) { - int ret; - - ret = ocfs2_reflink_remap_range(file_in, pos_in, file_out, pos_out, - len, true); - return ret < 0 ? ret : len; + return ocfs2_reflink_remap_range(file_in, pos_in, file_out, pos_out, + len, CLONERANGE_DEDUPE | CLONERANGE_SHORT); } const struct inode_operations ocfs2_file_iops = { diff --git a/fs/ocfs2/refcounttree.c b/fs/ocfs2/refcounttree.c index 02283c38b5a4..60be5c76db6d 100644 --- a/fs/ocfs2/refcounttree.c +++ b/fs/ocfs2/refcounttree.c @@ -4499,7 +4499,7 @@ static int ocfs2_reflink_update_dest(struct inode *dest, } /* Remap the range pos_in:len in s_inode to pos_out:len in t_inode. */ -static int ocfs2_reflink_remap_extent(struct inode *s_inode, +static s64 ocfs2_reflink_remap_extent(struct inode *s_inode, struct buffer_head *s_bh, loff_t pos_in, struct inode *t_inode, @@ -4514,6 +4514,7 @@ static int ocfs2_reflink_remap_extent(struct inode *s_inode, struct buffer_head *ref_root_bh = NULL; struct ocfs2_refcount_tree *ref_tree; struct ocfs2_super *osb; + s64 remapped = 0; loff_t pstart, plen; u32 p_cluster, num_clusters, slast, spos, tpos; unsigned int ext_flags; @@ -4597,18 +4598,20 @@ static int ocfs2_reflink_remap_extent(struct inode *s_inode, next_loop: spos += num_clusters; tpos += num_clusters; + remapped += ocfs2_clusters_to_bytes(t_inode->i_sb, + num_clusters); } -out: - return ret; + return remapped; out_unlock_refcount: ocfs2_unlock_refcount_tree(osb, ref_tree, 1); brelse(ref_root_bh); - return ret; +out: + return remapped > 0 ? remapped : ret; } /* Set up refcount tree and remap s_inode to t_inode. */ -static int ocfs2_reflink_remap_blocks(struct inode *s_inode, +static s64 ocfs2_reflink_remap_blocks(struct inode *s_inode, struct buffer_head *s_bh, loff_t pos_in, struct inode *t_inode, @@ -4620,7 +4623,7 @@ static int ocfs2_reflink_remap_blocks(struct inode *s_inode, struct ocfs2_super *osb; struct ocfs2_dinode *dis; struct ocfs2_dinode *dit; - int ret; + s64 ret; osb = OCFS2_SB(s_inode->i_sb); dis = (struct ocfs2_dinode *)s_bh->b_data; @@ -4692,7 +4695,7 @@ static int ocfs2_reflink_remap_blocks(struct inode *s_inode, /* Actually remap extents now. */ ret = ocfs2_reflink_remap_extent(s_inode, s_bh, pos_in, t_inode, t_bh, pos_out, len, &dealloc); - if (ret) { + if (ret < 0) { mlog_errno(ret); goto out; } @@ -4812,18 +4815,19 @@ static void ocfs2_reflink_inodes_unlock(struct inode *s_inode, } /* Link a range of blocks from one file to another. */ -int ocfs2_reflink_remap_range(struct file *file_in, +s64 ocfs2_reflink_remap_range(struct file *file_in, loff_t pos_in, struct file *file_out, loff_t pos_out, u64 len, - bool is_dedupe) + unsigned int flags) { struct inode *inode_in = file_inode(file_in); struct inode *inode_out = file_inode(file_out); struct ocfs2_super *osb = OCFS2_SB(inode_in->i_sb); struct buffer_head *in_bh = NULL, *out_bh = NULL; bool same_inode = (inode_in == inode_out); + s64 remapped = 0; ssize_t ret; if (!ocfs2_refcount_tree(osb)) @@ -4843,7 +4847,7 @@ int ocfs2_reflink_remap_range(struct file *file_in, goto out_unlock; ret = vfs_clone_file_prep(file_in, pos_in, file_out, pos_out, - &len, is_dedupe ? CLONERANGE_DEDUPE : 0); + &len, flags); if (ret <= 0) goto out_unlock; @@ -4857,12 +4861,13 @@ int ocfs2_reflink_remap_range(struct file *file_in, truncate_inode_pages_range(&inode_out->i_data, pos_out, PAGE_ALIGN(pos_out + len) - 1); - ret = ocfs2_reflink_remap_blocks(inode_in, in_bh, pos_in, inode_out, - out_bh, pos_out, len); + remapped = ocfs2_reflink_remap_blocks(inode_in, in_bh, pos_in, + inode_out, out_bh, pos_out, len); up_write(&OCFS2_I(inode_in)->ip_alloc_sem); if (!same_inode) up_write(&OCFS2_I(inode_out)->ip_alloc_sem); - if (ret) { + if (remapped < 0) { + ret = remapped; mlog_errno(ret); goto out_unlock; } @@ -4881,9 +4886,9 @@ int ocfs2_reflink_remap_range(struct file *file_in, } ocfs2_reflink_inodes_unlock(inode_in, in_bh, inode_out, out_bh); - return 0; + return remapped; out_unlock: ocfs2_reflink_inodes_unlock(inode_in, in_bh, inode_out, out_bh); - return ret; + return remapped > 0 ? remapped : ret; } diff --git a/fs/ocfs2/refcounttree.h b/fs/ocfs2/refcounttree.h index 4af55bf4b35b..410a3145a06a 100644 --- a/fs/ocfs2/refcounttree.h +++ b/fs/ocfs2/refcounttree.h @@ -115,11 +115,11 @@ int ocfs2_reflink_ioctl(struct inode *inode, const char __user *oldname, const char __user *newname, bool preserve); -int ocfs2_reflink_remap_range(struct file *file_in, +s64 ocfs2_reflink_remap_range(struct file *file_in, loff_t pos_in, struct file *file_out, loff_t pos_out, u64 len, - bool is_dedupe); + unsigned int flags); #endif /* OCFS2_REFCOUNTTREE_H */
WARNING: multiple messages have this Message-ID (diff)
From: Darrick J. Wong <darrick.wong@oracle.com> To: david@fromorbit.com, darrick.wong@oracle.com Cc: linux-xfs@vger.kernel.org, linux-fsdevel@vger.kernel.org, linux-btrfs@vger.kernel.org, ocfs2-devel@oss.oracle.com, sandeen@redhat.com Subject: [Ocfs2-devel] [PATCH 14/15] ocfs2: support partial clone range and dedupe range Date: Thu, 04 Oct 2018 17:46:20 -0700 [thread overview] Message-ID: <153870038054.29072.6999468698657448422.stgit@magnolia> (raw) In-Reply-To: <153870027422.29072.7433543674436957232.stgit@magnolia> From: Darrick J. Wong <darrick.wong@oracle.com> Change the ocfs2 remap code to allow for returning partial results. Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com> --- fs/ocfs2/file.c | 14 ++++---------- fs/ocfs2/refcounttree.c | 35 ++++++++++++++++++++--------------- fs/ocfs2/refcounttree.h | 4 ++-- 3 files changed, 26 insertions(+), 27 deletions(-) diff --git a/fs/ocfs2/file.c b/fs/ocfs2/file.c index 1ee6d3ecdac6..4562111259b4 100644 --- a/fs/ocfs2/file.c +++ b/fs/ocfs2/file.c @@ -2534,11 +2534,8 @@ static s64 ocfs2_file_clone_range(struct file *file_in, u64 len, unsigned int flags) { - int ret; - - ret = ocfs2_reflink_remap_range(file_in, pos_in, file_out, pos_out, - len, false); - return ret < 0 ? ret : len; + return ocfs2_reflink_remap_range(file_in, pos_in, file_out, pos_out, + len, flags); } static s64 ocfs2_file_dedupe_range(struct file *file_in, @@ -2547,11 +2544,8 @@ static s64 ocfs2_file_dedupe_range(struct file *file_in, loff_t pos_out, u64 len) { - int ret; - - ret = ocfs2_reflink_remap_range(file_in, pos_in, file_out, pos_out, - len, true); - return ret < 0 ? ret : len; + return ocfs2_reflink_remap_range(file_in, pos_in, file_out, pos_out, + len, CLONERANGE_DEDUPE | CLONERANGE_SHORT); } const struct inode_operations ocfs2_file_iops = { diff --git a/fs/ocfs2/refcounttree.c b/fs/ocfs2/refcounttree.c index 02283c38b5a4..60be5c76db6d 100644 --- a/fs/ocfs2/refcounttree.c +++ b/fs/ocfs2/refcounttree.c @@ -4499,7 +4499,7 @@ static int ocfs2_reflink_update_dest(struct inode *dest, } /* Remap the range pos_in:len in s_inode to pos_out:len in t_inode. */ -static int ocfs2_reflink_remap_extent(struct inode *s_inode, +static s64 ocfs2_reflink_remap_extent(struct inode *s_inode, struct buffer_head *s_bh, loff_t pos_in, struct inode *t_inode, @@ -4514,6 +4514,7 @@ static int ocfs2_reflink_remap_extent(struct inode *s_inode, struct buffer_head *ref_root_bh = NULL; struct ocfs2_refcount_tree *ref_tree; struct ocfs2_super *osb; + s64 remapped = 0; loff_t pstart, plen; u32 p_cluster, num_clusters, slast, spos, tpos; unsigned int ext_flags; @@ -4597,18 +4598,20 @@ static int ocfs2_reflink_remap_extent(struct inode *s_inode, next_loop: spos += num_clusters; tpos += num_clusters; + remapped += ocfs2_clusters_to_bytes(t_inode->i_sb, + num_clusters); } -out: - return ret; + return remapped; out_unlock_refcount: ocfs2_unlock_refcount_tree(osb, ref_tree, 1); brelse(ref_root_bh); - return ret; +out: + return remapped > 0 ? remapped : ret; } /* Set up refcount tree and remap s_inode to t_inode. */ -static int ocfs2_reflink_remap_blocks(struct inode *s_inode, +static s64 ocfs2_reflink_remap_blocks(struct inode *s_inode, struct buffer_head *s_bh, loff_t pos_in, struct inode *t_inode, @@ -4620,7 +4623,7 @@ static int ocfs2_reflink_remap_blocks(struct inode *s_inode, struct ocfs2_super *osb; struct ocfs2_dinode *dis; struct ocfs2_dinode *dit; - int ret; + s64 ret; osb = OCFS2_SB(s_inode->i_sb); dis = (struct ocfs2_dinode *)s_bh->b_data; @@ -4692,7 +4695,7 @@ static int ocfs2_reflink_remap_blocks(struct inode *s_inode, /* Actually remap extents now. */ ret = ocfs2_reflink_remap_extent(s_inode, s_bh, pos_in, t_inode, t_bh, pos_out, len, &dealloc); - if (ret) { + if (ret < 0) { mlog_errno(ret); goto out; } @@ -4812,18 +4815,19 @@ static void ocfs2_reflink_inodes_unlock(struct inode *s_inode, } /* Link a range of blocks from one file to another. */ -int ocfs2_reflink_remap_range(struct file *file_in, +s64 ocfs2_reflink_remap_range(struct file *file_in, loff_t pos_in, struct file *file_out, loff_t pos_out, u64 len, - bool is_dedupe) + unsigned int flags) { struct inode *inode_in = file_inode(file_in); struct inode *inode_out = file_inode(file_out); struct ocfs2_super *osb = OCFS2_SB(inode_in->i_sb); struct buffer_head *in_bh = NULL, *out_bh = NULL; bool same_inode = (inode_in == inode_out); + s64 remapped = 0; ssize_t ret; if (!ocfs2_refcount_tree(osb)) @@ -4843,7 +4847,7 @@ int ocfs2_reflink_remap_range(struct file *file_in, goto out_unlock; ret = vfs_clone_file_prep(file_in, pos_in, file_out, pos_out, - &len, is_dedupe ? CLONERANGE_DEDUPE : 0); + &len, flags); if (ret <= 0) goto out_unlock; @@ -4857,12 +4861,13 @@ int ocfs2_reflink_remap_range(struct file *file_in, truncate_inode_pages_range(&inode_out->i_data, pos_out, PAGE_ALIGN(pos_out + len) - 1); - ret = ocfs2_reflink_remap_blocks(inode_in, in_bh, pos_in, inode_out, - out_bh, pos_out, len); + remapped = ocfs2_reflink_remap_blocks(inode_in, in_bh, pos_in, + inode_out, out_bh, pos_out, len); up_write(&OCFS2_I(inode_in)->ip_alloc_sem); if (!same_inode) up_write(&OCFS2_I(inode_out)->ip_alloc_sem); - if (ret) { + if (remapped < 0) { + ret = remapped; mlog_errno(ret); goto out_unlock; } @@ -4881,9 +4886,9 @@ int ocfs2_reflink_remap_range(struct file *file_in, } ocfs2_reflink_inodes_unlock(inode_in, in_bh, inode_out, out_bh); - return 0; + return remapped; out_unlock: ocfs2_reflink_inodes_unlock(inode_in, in_bh, inode_out, out_bh); - return ret; + return remapped > 0 ? remapped : ret; } diff --git a/fs/ocfs2/refcounttree.h b/fs/ocfs2/refcounttree.h index 4af55bf4b35b..410a3145a06a 100644 --- a/fs/ocfs2/refcounttree.h +++ b/fs/ocfs2/refcounttree.h @@ -115,11 +115,11 @@ int ocfs2_reflink_ioctl(struct inode *inode, const char __user *oldname, const char __user *newname, bool preserve); -int ocfs2_reflink_remap_range(struct file *file_in, +s64 ocfs2_reflink_remap_range(struct file *file_in, loff_t pos_in, struct file *file_out, loff_t pos_out, u64 len, - bool is_dedupe); + unsigned int flags); #endif /* OCFS2_REFCOUNTTREE_H */
next prev parent reply other threads:[~2018-10-05 0:46 UTC|newest] Thread overview: 82+ messages / expand[flat|nested] mbox.gz Atom feed top 2018-10-05 0:44 [PATCH 00/15] fs: fixes for serious clone/dedupe problems Darrick J. Wong 2018-10-05 0:44 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 0:44 ` [PATCH 01/15] xfs: add a per-xfs trace_printk macro Darrick J. Wong 2018-10-05 0:44 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 0:44 ` [PATCH 02/15] xfs: refactor clonerange preparation into a separate helper Darrick J. Wong 2018-10-05 0:44 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 5:28 ` Dave Chinner 2018-10-05 5:28 ` [Ocfs2-devel] " Dave Chinner 2018-10-05 17:06 ` Darrick J. Wong 2018-10-05 17:06 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-06 10:30 ` Christoph Hellwig 2018-10-06 10:30 ` [Ocfs2-devel] " Christoph Hellwig 2018-10-05 7:02 ` Dave Chinner 2018-10-05 7:02 ` [Ocfs2-devel] " Dave Chinner 2018-10-05 9:02 ` Dave Chinner 2018-10-05 9:02 ` [Ocfs2-devel] " Dave Chinner 2018-10-05 17:21 ` Darrick J. Wong 2018-10-05 17:21 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 23:42 ` Dave Chinner 2018-10-05 23:42 ` [Ocfs2-devel] " Dave Chinner 2018-10-05 0:44 ` [PATCH 03/15] xfs: zero posteof blocks when cloning above eof Darrick J. Wong 2018-10-05 0:44 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 5:28 ` Dave Chinner 2018-10-05 5:28 ` [Ocfs2-devel] " Dave Chinner 2018-10-06 10:34 ` Christoph Hellwig 2018-10-06 10:34 ` [Ocfs2-devel] " Christoph Hellwig 2018-10-05 0:45 ` [PATCH 04/15] xfs: update ctime and remove suid before cloning files Darrick J. Wong 2018-10-05 0:45 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 5:30 ` Dave Chinner 2018-10-05 5:30 ` [Ocfs2-devel] " Dave Chinner 2018-10-06 10:35 ` Christoph Hellwig 2018-10-06 10:35 ` [Ocfs2-devel] " Christoph Hellwig 2018-10-05 0:45 ` [PATCH 05/15] vfs: check file ranges " Darrick J. Wong 2018-10-05 0:45 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-06 10:38 ` Christoph Hellwig 2018-10-06 10:38 ` [Ocfs2-devel] " Christoph Hellwig 2018-10-05 0:45 ` [PATCH 06/15] vfs: strengthen checking of file range inputs to clone/dedupe range Darrick J. Wong 2018-10-05 0:45 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 6:10 ` Amir Goldstein 2018-10-05 17:36 ` Darrick J. Wong 2018-10-05 17:36 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 0:45 ` [PATCH 07/15] vfs: skip zero-length dedupe requests Darrick J. Wong 2018-10-05 0:45 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 8:39 ` Amir Goldstein 2018-10-06 10:39 ` Christoph Hellwig 2018-10-06 10:39 ` [Ocfs2-devel] " Christoph Hellwig 2018-10-05 0:45 ` [PATCH 08/15] vfs: change clone and dedupe range function pointers to return bytes completed Darrick J. Wong 2018-10-05 0:45 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 8:06 ` Amir Goldstein 2018-10-05 21:47 ` Darrick J. Wong 2018-10-05 21:47 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-06 10:41 ` Christoph Hellwig 2018-10-06 10:41 ` [Ocfs2-devel] " Christoph Hellwig 2018-10-08 18:59 ` Darrick J. Wong 2018-10-08 18:59 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 0:45 ` [PATCH 09/15] vfs: pass operation flags to {clone, dedupe}_file_range implementations Darrick J. Wong 2018-10-05 0:45 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 7:07 ` Amir Goldstein 2018-10-05 17:50 ` Darrick J. Wong 2018-10-05 17:50 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-06 10:44 ` Christoph Hellwig 2018-10-06 10:44 ` [Ocfs2-devel] " Christoph Hellwig 2018-10-05 0:45 ` [PATCH 10/15] vfs: make cloning to source file eof more explicit Darrick J. Wong 2018-10-05 0:45 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 6:47 ` Amir Goldstein 2018-10-05 0:45 ` [PATCH 11/15] vfs: allow short clone and dedupe operations Darrick J. Wong 2018-10-05 0:45 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 0:46 ` [PATCH 12/15] vfs: implement opportunistic short dedupe Darrick J. Wong 2018-10-05 0:46 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 6:40 ` Amir Goldstein 2018-10-05 17:42 ` Darrick J. Wong 2018-10-05 17:42 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 0:46 ` [PATCH 13/15] ocfs2: truncate page cache for clone destination file before remapping Darrick J. Wong 2018-10-05 0:46 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 0:46 ` Darrick J. Wong [this message] 2018-10-05 0:46 ` [Ocfs2-devel] [PATCH 14/15] ocfs2: support partial clone range and dedupe range Darrick J. Wong 2018-10-05 0:46 ` [PATCH 15/15] xfs: support returning partial reflink results Darrick J. Wong 2018-10-05 0:46 ` [Ocfs2-devel] " Darrick J. Wong 2018-10-05 1:17 ` [PATCH 00/15] fs: fixes for serious clone/dedupe problems Dave Chinner 2018-10-05 1:17 ` [Ocfs2-devel] " Dave Chinner 2018-10-05 1:24 ` Darrick J. Wong 2018-10-05 1:24 ` [Ocfs2-devel] " Darrick J. Wong
Reply instructions: You may reply publicly to this message via plain-text email using any one of the following methods: * Save the following mbox file, import it into your mail client, and reply-to-all from there: mbox Avoid top-posting and favor interleaved quoting: https://en.wikipedia.org/wiki/Posting_style#Interleaved_style * Reply using the --to, --cc, and --in-reply-to switches of git-send-email(1): git send-email \ --in-reply-to=153870038054.29072.6999468698657448422.stgit@magnolia \ --to=darrick.wong@oracle.com \ --cc=david@fromorbit.com \ --cc=linux-btrfs@vger.kernel.org \ --cc=linux-fsdevel@vger.kernel.org \ --cc=linux-xfs@vger.kernel.org \ --cc=ocfs2-devel@oss.oracle.com \ --cc=sandeen@redhat.com \ /path/to/YOUR_REPLY https://kernel.org/pub/software/scm/git/docs/git-send-email.html * If your mail client supports setting the In-Reply-To header via mailto: links, try the mailto: linkBe sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes, see mirroring instructions on how to clone and mirror all data and code used by this external index.