summaryrefslogtreecommitdiffstats
path: root/fs/xfs/xfs_bmap_util.c
diff options
context:
space:
mode:
authorChristoph Hellwig2017-10-17 23:16:19 +0200
committerDarrick J. Wong2017-10-27 00:38:20 +0200
commit232b51948b99dfcc95e81d8a289bc0409b3ff5b3 (patch)
tree1fccfa555e5615315aa2ded63028f4d5fc7799bf /fs/xfs/xfs_bmap_util.c
parentxfs: rewrite getbmap using the xfs_iext_* helpers (diff)
downloadkernel-qcow2-linux-232b51948b99dfcc95e81d8a289bc0409b3ff5b3.tar.gz
kernel-qcow2-linux-232b51948b99dfcc95e81d8a289bc0409b3ff5b3.tar.xz
kernel-qcow2-linux-232b51948b99dfcc95e81d8a289bc0409b3ff5b3.zip
xfs: simplify the xfs_getbmap interface
Instead of passing in a formatter callback allocate the bmap buffer in the caller and process the entries there. Additionally replace the in-kernel buffer with a new much smaller structure, and unify the implementation of the different ioctls in a single function. Signed-off-by: Christoph Hellwig <hch@lst.de> Reviewed-by: Brian Foster <bfoster@redhat.com> Reviewed-by: Darrick J. Wong <darrick.wong@oracle.com> Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
Diffstat (limited to 'fs/xfs/xfs_bmap_util.c')
-rw-r--r--fs/xfs/xfs_bmap_util.c38
1 files changed, 9 insertions, 29 deletions
diff --git a/fs/xfs/xfs_bmap_util.c b/fs/xfs/xfs_bmap_util.c
index 2564b8b33e99..0543423651ff 100644
--- a/fs/xfs/xfs_bmap_util.c
+++ b/fs/xfs/xfs_bmap_util.c
@@ -409,11 +409,11 @@ static int
xfs_getbmap_report_one(
struct xfs_inode *ip,
struct getbmapx *bmv,
- struct getbmapx *out,
+ struct kgetbmap *out,
int64_t bmv_end,
struct xfs_bmbt_irec *got)
{
- struct getbmapx *p = out + bmv->bmv_entries;
+ struct kgetbmap *p = out + bmv->bmv_entries;
bool shared = false, trimmed = false;
int error;
@@ -460,12 +460,12 @@ static void
xfs_getbmap_report_hole(
struct xfs_inode *ip,
struct getbmapx *bmv,
- struct getbmapx *out,
+ struct kgetbmap *out,
int64_t bmv_end,
xfs_fileoff_t bno,
xfs_fileoff_t end)
{
- struct getbmapx *p = out + bmv->bmv_entries;
+ struct kgetbmap *p = out + bmv->bmv_entries;
if (bmv->bmv_iflags & BMV_IF_NO_HOLES)
return;
@@ -513,47 +513,36 @@ xfs_getbmap_next_rec(
*/
int /* error code */
xfs_getbmap(
- xfs_inode_t *ip,
+ struct xfs_inode *ip,
struct getbmapx *bmv, /* user bmap structure */
- xfs_bmap_format_t formatter, /* format to user */
- void *arg) /* formatter arg */
+ struct kgetbmap *out)
{
struct xfs_mount *mp = ip->i_mount;
int iflags = bmv->bmv_iflags;
- int whichfork, lock, i, error = 0;
+ int whichfork, lock, error = 0;
int64_t bmv_end, max_len;
xfs_fileoff_t bno, first_bno;
struct xfs_ifork *ifp;
- struct getbmapx *out;
struct xfs_bmbt_irec got, rec;
xfs_filblks_t len;
xfs_extnum_t idx;
+ if (bmv->bmv_iflags & ~BMV_IF_VALID)
+ return -EINVAL;
#ifndef DEBUG
/* Only allow CoW fork queries if we're debugging. */
if (iflags & BMV_IF_COWFORK)
return -EINVAL;
#endif
-
if ((iflags & BMV_IF_ATTRFORK) && (iflags & BMV_IF_COWFORK))
return -EINVAL;
- if (bmv->bmv_count <= 1)
- return -EINVAL;
- if (bmv->bmv_count > ULONG_MAX / sizeof(struct getbmapx))
- return -ENOMEM;
-
if (bmv->bmv_length < -1)
return -EINVAL;
-
bmv->bmv_entries = 0;
if (bmv->bmv_length == 0)
return 0;
- out = kmem_zalloc_large(bmv->bmv_count * sizeof(struct getbmapx), 0);
- if (!out)
- return -ENOMEM;
-
if (iflags & BMV_IF_ATTRFORK)
whichfork = XFS_ATTR_FORK;
else if (iflags & BMV_IF_COWFORK)
@@ -700,15 +689,6 @@ out_unlock_ilock:
xfs_iunlock(ip, lock);
out_unlock_iolock:
xfs_iunlock(ip, XFS_IOLOCK_SHARED);
-
- for (i = 0; i < bmv->bmv_entries; i++) {
- /* format results & advance arg */
- error = formatter(&arg, &out[i]);
- if (error)
- break;
- }
-
- kmem_free(out);
return error;
}