mirror of
https://github.com/BobTheBlinker/android_kernel_motorola_sm6375.git
synced 2026-10-26 06:33:19 -04:00
UPSTREAM: ANDROID: fuse-bpf: Add support for FUSE_COPY_FILE_RANGE
Bug: 217570523 Test: generic/075 Signed-off-by: Daniel Rosenberg <drosen@google.com> Change-Id: I5feb75c83bc8bca2f44700d731f9f43e1eacf77c
This commit is contained in:
parent
d932a916a2
commit
03c20048f7
3 changed files with 89 additions and 0 deletions
|
|
@ -403,6 +403,64 @@ void *fuse_flush_finalize(struct fuse_args *fa, struct file *file, fl_owner_t id
|
|||
return NULL;
|
||||
}
|
||||
|
||||
int fuse_copy_file_range_initialize(struct fuse_args *fa, struct fuse_copy_file_range_io *fcf,
|
||||
struct file *file_in, loff_t pos_in, struct file *file_out,
|
||||
loff_t pos_out, size_t len, unsigned int flags)
|
||||
{
|
||||
struct fuse_file *fuse_file_in = file_in->private_data;
|
||||
struct fuse_file *fuse_file_out = file_out->private_data;
|
||||
|
||||
|
||||
fcf->fci = (struct fuse_copy_file_range_in) {
|
||||
.fh_in = fuse_file_in->fh,
|
||||
.off_in = pos_in,
|
||||
.nodeid_out = fuse_file_out->nodeid,
|
||||
.fh_out = fuse_file_out->fh,
|
||||
.off_out = pos_out,
|
||||
.len = len,
|
||||
.flags = flags,
|
||||
};
|
||||
|
||||
*fa = (struct fuse_args) {
|
||||
.nodeid = get_node_id(file_in->f_inode),
|
||||
.opcode = FUSE_COPY_FILE_RANGE,
|
||||
.in_numargs = 1,
|
||||
.in_args[0].size = sizeof(fcf->fci),
|
||||
.in_args[0].value = &fcf->fci,
|
||||
.out_numargs = 1,
|
||||
.out_args[0].size = sizeof(fcf->fwo),
|
||||
.out_args[0].value = &fcf->fwo,
|
||||
};
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int fuse_copy_file_range_backing(struct fuse_args *fa, struct file *file_in, loff_t pos_in,
|
||||
struct file *file_out, loff_t pos_out, size_t len,
|
||||
unsigned int flags)
|
||||
{
|
||||
const struct fuse_copy_file_range_in *fci = fa->in_args[0].value;
|
||||
struct fuse_file *fuse_file_in = file_in->private_data;
|
||||
struct file *backing_file_in = fuse_file_in->backing_file;
|
||||
struct fuse_file *fuse_file_out = file_out->private_data;
|
||||
struct file *backing_file_out = fuse_file_out->backing_file;
|
||||
|
||||
/* TODO: Handle changing of in/out files */
|
||||
if (backing_file_out)
|
||||
return vfs_copy_file_range(backing_file_in, fci->off_in, backing_file_out,
|
||||
fci->off_out, fci->len, fci->flags);
|
||||
else
|
||||
return generic_copy_file_range(file_in, pos_in, file_out, pos_out, len,
|
||||
flags);
|
||||
}
|
||||
|
||||
void *fuse_copy_file_range_finalize(struct fuse_args *fa, struct file *file_in, loff_t pos_in,
|
||||
struct file *file_out, loff_t pos_out, size_t len,
|
||||
unsigned int flags)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
int fuse_fsync_initialize(struct fuse_args *fa, struct fuse_fsync_in *ffi,
|
||||
struct file *file, loff_t start, loff_t end, int datasync)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -3540,6 +3540,18 @@ static ssize_t __fuse_copy_file_range(struct file *file_in, loff_t pos_in,
|
|||
bool is_unstable = (!fc->writeback_cache) &&
|
||||
((pos_out + len) > inode_out->i_size);
|
||||
|
||||
#ifdef CONFIG_FUSE_BPF
|
||||
struct fuse_err_ret fer;
|
||||
|
||||
fer = fuse_bpf_backing(file_in->f_inode, struct fuse_copy_file_range_io,
|
||||
fuse_copy_file_range_initialize,
|
||||
fuse_copy_file_range_backing,
|
||||
fuse_copy_file_range_finalize,
|
||||
file_in, pos_in, file_out, pos_out, len, flags);
|
||||
if (fer.ret)
|
||||
return PTR_ERR(fer.result);
|
||||
#endif
|
||||
|
||||
if (fc->no_copy_file_range)
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
|
|
|
|||
|
|
@ -1431,6 +1431,25 @@ int fuse_flush_backing(struct fuse_args *fa, struct file *file, fl_owner_t id);
|
|||
void *fuse_flush_finalize(struct fuse_args *fa,
|
||||
struct file *file, fl_owner_t id);
|
||||
|
||||
struct fuse_copy_file_range_io {
|
||||
struct fuse_copy_file_range_in fci;
|
||||
struct fuse_write_out fwo;
|
||||
};
|
||||
|
||||
int fuse_copy_file_range_initialize(struct fuse_args *fa,
|
||||
struct fuse_copy_file_range_io *fcf,
|
||||
struct file *file_in, loff_t pos_in,
|
||||
struct file *file_out, loff_t pos_out,
|
||||
size_t len, unsigned int flags);
|
||||
int fuse_copy_file_range_backing(struct fuse_args *fa,
|
||||
struct file *file_in, loff_t pos_in,
|
||||
struct file *file_out, loff_t pos_out,
|
||||
size_t len, unsigned int flags);
|
||||
void *fuse_copy_file_range_finalize(struct fuse_args *fa,
|
||||
struct file *file_in, loff_t pos_in,
|
||||
struct file *file_out, loff_t pos_out,
|
||||
size_t len, unsigned int flags);
|
||||
|
||||
int fuse_fsync_initialize(struct fuse_args *fa, struct fuse_fsync_in *ffi,
|
||||
struct file *file, loff_t start, loff_t end, int datasync);
|
||||
int fuse_fsync_backing(struct fuse_args *fa,
|
||||
|
|
|
|||
Loading…
Reference in a new issue