Change release ioctl to be denominated in bytes not blocks

This more closely matches stage ioctl and other conventions.

Also change release code to use offset/length nomenclature for consistency.

Signed-off-by: Andy Grover <agrover@versity.com>
This commit is contained in:
Andy Grover
2021-01-05 11:59:54 -08:00
parent 64a698aa93
commit 2c5871c253
4 changed files with 43 additions and 39 deletions

View File

@@ -274,8 +274,8 @@ static long scoutfs_ioc_release(struct file *file, unsigned long arg)
struct super_block *sb = inode->i_sb;
struct scoutfs_ioctl_release args;
struct scoutfs_lock *lock = NULL;
loff_t start;
loff_t end_inc;
u64 sblock;
u64 eblock;
u64 online;
u64 offline;
u64 isize;
@@ -286,9 +286,11 @@ static long scoutfs_ioc_release(struct file *file, unsigned long arg)
trace_scoutfs_ioc_release(sb, scoutfs_ino(inode), &args);
if (args.count == 0)
if (args.length == 0)
return 0;
if ((args.block + args.count) < args.block)
if (((args.offset + args.length) < args.offset) ||
(args.offset & SCOUTFS_BLOCK_SM_MASK) ||
(args.length & SCOUTFS_BLOCK_SM_MASK))
return -EINVAL;
@@ -321,23 +323,24 @@ static long scoutfs_ioc_release(struct file *file, unsigned long arg)
inode_dio_wait(inode);
/* drop all clean and dirty cached blocks in the range */
start = args.block << SCOUTFS_BLOCK_SM_SHIFT;
end_inc = ((args.block + args.count) << SCOUTFS_BLOCK_SM_SHIFT) - 1;
truncate_inode_pages_range(&inode->i_data, start, end_inc);
truncate_inode_pages_range(&inode->i_data, args.offset,
args.offset + args.length - 1);
sblock = args.offset >> SCOUTFS_BLOCK_SM_SHIFT;
eblock = (args.offset + args.length - 1) >> SCOUTFS_BLOCK_SM_SHIFT;
ret = scoutfs_data_truncate_items(sb, inode, scoutfs_ino(inode),
args.block,
args.block + args.count - 1, true,
sblock,
eblock, true,
lock);
if (ret == 0) {
scoutfs_inode_get_onoff(inode, &online, &offline);
isize = i_size_read(inode);
if (online == 0 && isize) {
start = (isize + SCOUTFS_BLOCK_SM_SIZE - 1)
sblock = (isize + SCOUTFS_BLOCK_SM_SIZE - 1)
>> SCOUTFS_BLOCK_SM_SHIFT;
ret = scoutfs_data_truncate_items(sb, inode,
scoutfs_ino(inode),
start, U64_MAX,
sblock, U64_MAX,
false, lock);
}
}
@@ -459,23 +462,24 @@ static long scoutfs_ioc_stage(struct file *file, unsigned long arg)
trace_scoutfs_ioc_stage(sb, scoutfs_ino(inode), &args);
end_size = args.offset + args.count;
end_size = args.offset + args.length;
/* verify arg constraints that aren't dependent on file */
if (args.count < 0 || (end_size < args.offset) ||
args.offset & SCOUTFS_BLOCK_SM_MASK)
if (args.length < 0 || (end_size < args.offset) ||
args.offset & SCOUTFS_BLOCK_SM_MASK) {
return -EINVAL;
}
if (args.count == 0)
if (args.length == 0)
return 0;
/* the iocb is really only used for the file pointer :P */
init_sync_kiocb(&kiocb, file);
kiocb.ki_pos = args.offset;
kiocb.ki_left = args.count;
kiocb.ki_nbytes = args.count;
kiocb.ki_left = args.length;
kiocb.ki_nbytes = args.length;
iov.iov_base = (void __user *)(unsigned long)args.buf_ptr;
iov.iov_len = args.count;
iov.iov_len = args.length;
ret = mnt_want_write_file(file);
if (ret)
@@ -514,11 +518,11 @@ static long scoutfs_ioc_stage(struct file *file, unsigned long arg)
written = 0;
do {
ret = generic_file_buffered_write(&kiocb, &iov, 1, pos, &pos,
args.count, written);
args.length, written);
BUG_ON(ret == -EIOCBQUEUED);
if (ret > 0)
written += ret;
} while (ret > 0 && written < args.count);
} while (ret > 0 && written < args.length);
si->staging = false;
current->backing_dev_info = NULL;

View File

@@ -176,8 +176,8 @@ struct scoutfs_ioctl_ino_path_result {
* an offline record is left behind to trigger demand staging if the
* file is read.
*
* The starting block offset and number of blocks to release are in
* units 4KB blocks.
* The starting file offset and number of bytes to release must be in
* multiples of 4KB.
*
* The specified range can extend past i_size and can straddle sparse
* regions or blocks that are already offline. The only change it makes
@@ -193,8 +193,8 @@ struct scoutfs_ioctl_ino_path_result {
* presentation of the data in the file.
*/
struct scoutfs_ioctl_release {
__u64 block;
__u64 count;
__u64 offset;
__u64 length;
__u64 data_version;
};
@@ -205,7 +205,7 @@ struct scoutfs_ioctl_stage {
__u64 data_version;
__u64 buf_ptr;
__u64 offset;
__s32 count;
__s32 length;
__u32 _pad;
};

View File

@@ -530,22 +530,22 @@ TRACE_EVENT(scoutfs_ioc_release,
TP_STRUCT__entry(
SCSB_TRACE_FIELDS
__field(__u64, ino)
__field(__u64, block)
__field(__u64, count)
__field(__u64, offset)
__field(__u64, length)
__field(__u64, vers)
),
TP_fast_assign(
SCSB_TRACE_ASSIGN(sb);
__entry->ino = ino;
__entry->block = args->block;
__entry->count = args->count;
__entry->offset = args->offset;
__entry->length = args->length;
__entry->vers = args->data_version;
),
TP_printk(SCSBF" ino %llu block %llu count %llu vers %llu",
SCSB_TRACE_ARGS, __entry->ino, __entry->block,
__entry->count, __entry->vers)
TP_printk(SCSBF" ino %llu offset %llu length %llu vers %llu",
SCSB_TRACE_ARGS, __entry->ino, __entry->offset,
__entry->length, __entry->vers)
);
DEFINE_EVENT(scoutfs_ino_ret_class, scoutfs_ioc_release_ret,
@@ -564,7 +564,7 @@ TRACE_EVENT(scoutfs_ioc_stage,
__field(__u64, ino)
__field(__u64, vers)
__field(__u64, offset)
__field(__s32, count)
__field(__s32, length)
),
TP_fast_assign(
@@ -572,12 +572,12 @@ TRACE_EVENT(scoutfs_ioc_stage,
__entry->ino = ino;
__entry->vers = args->data_version;
__entry->offset = args->offset;
__entry->count = args->count;
__entry->length = args->length;
),
TP_printk(SCSBF" ino %llu vers %llu offset %llu count %d",
TP_printk(SCSBF" ino %llu vers %llu offset %llu length %d",
SCSB_TRACE_ARGS, __entry->ino, __entry->vers,
__entry->offset, __entry->count)
__entry->offset, __entry->length)
);
TRACE_EVENT(scoutfs_ioc_data_wait_err,

View File

@@ -76,7 +76,7 @@ static int do_stage(struct stage_args *args)
ioctl_args.data_version = args->data_version;
ioctl_args.buf_ptr = (unsigned long)buf;
ioctl_args.offset = args->offset;
ioctl_args.count = bytes;
ioctl_args.length = bytes;
args->length -= bytes;
args->offset += bytes;
@@ -211,8 +211,8 @@ static int do_release(struct release_args *args)
assert(args->offset % SCOUTFS_BLOCK_SM_SIZE == 0);
assert(args->length % SCOUTFS_BLOCK_SM_SIZE == 0);
ioctl_args.block = args->offset / SCOUTFS_BLOCK_SM_SIZE;
ioctl_args.count = args->length / SCOUTFS_BLOCK_SM_SIZE;
ioctl_args.offset = args->offset;
ioctl_args.length = args->length;
ioctl_args.data_version = args->data_version;
ret = ioctl(fd, SCOUTFS_IOC_RELEASE, &ioctl_args);