Skip to content

Commit d1f5323

Browse files
committed
Merge branch 'work.splice_read' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs
Pull VFS splice updates from Al Viro: "There's a bunch of branches this cycle, both mine and from other folks and I'd rather send pull requests separately. This one is the conversion of ->splice_read() to ITER_PIPE iov_iter (and introduction of such). Gets rid of a lot of code in fs/splice.c and elsewhere; there will be followups, but these are for the next cycle... Some pipe/splice-related cleanups from Miklos in the same branch as well" * 'work.splice_read' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs: pipe: fix comment in pipe_buf_operations pipe: add pipe_buf_steal() helper pipe: add pipe_buf_confirm() helper pipe: add pipe_buf_release() helper pipe: add pipe_buf_get() helper relay: simplify relay_file_read() switch default_file_splice_read() to use of pipe-backed iov_iter switch generic_file_splice_read() to use of ->read_iter() new iov_iter flavour: pipe-backed fuse_dev_splice_read(): switch to add_to_pipe() skb_splice_bits(): get rid of callback new helper: add_to_pipe() splice: lift pipe_lock out of splice_to_pipe() splice: switch get_iovec_page_array() to iov_iter splice_to_pipe(): don't open-code wakeup_pipe_readers() consistent treatment of EFAULT on O_DIRECT read/write
2 parents 2eee010 + a949e63 commit d1f5323

30 files changed

+746
-1077
lines changed

Diff for: drivers/char/virtio_console.c

+1-1
Original file line numberDiff line numberDiff line change
@@ -889,7 +889,7 @@ static int pipe_to_sg(struct pipe_inode_info *pipe, struct pipe_buffer *buf,
889889
return 0;
890890

891891
/* Try lock this page */
892-
if (buf->ops->steal(pipe, buf) == 0) {
892+
if (pipe_buf_steal(pipe, buf) == 0) {
893893
/* Get reference and unlock page for moving */
894894
get_page(buf->page);
895895
unlock_page(buf->page);

Diff for: drivers/staging/lustre/lustre/llite/file.c

+25-64
Original file line numberDiff line numberDiff line change
@@ -1138,45 +1138,31 @@ ll_file_io_generic(const struct lu_env *env, struct vvp_io_args *args,
11381138
range_lock_init(&range, *ppos, *ppos + count - 1);
11391139

11401140
vio->vui_fd = LUSTRE_FPRIVATE(file);
1141-
vio->vui_io_subtype = args->via_io_subtype;
1141+
vio->vui_iter = args->u.normal.via_iter;
1142+
vio->vui_iocb = args->u.normal.via_iocb;
1143+
/*
1144+
* Direct IO reads must also take range lock,
1145+
* or multiple reads will try to work on the same pages
1146+
* See LU-6227 for details.
1147+
*/
1148+
if (((iot == CIT_WRITE) ||
1149+
(iot == CIT_READ && (file->f_flags & O_DIRECT))) &&
1150+
!(vio->vui_fd->fd_flags & LL_FILE_GROUP_LOCKED)) {
1151+
CDEBUG(D_VFSTRACE, "Range lock [%llu, %llu]\n",
1152+
range.rl_node.in_extent.start,
1153+
range.rl_node.in_extent.end);
1154+
result = range_lock(&lli->lli_write_tree,
1155+
&range);
1156+
if (result < 0)
1157+
goto out;
11421158

1143-
switch (vio->vui_io_subtype) {
1144-
case IO_NORMAL:
1145-
vio->vui_iter = args->u.normal.via_iter;
1146-
vio->vui_iocb = args->u.normal.via_iocb;
1147-
/*
1148-
* Direct IO reads must also take range lock,
1149-
* or multiple reads will try to work on the same pages
1150-
* See LU-6227 for details.
1151-
*/
1152-
if (((iot == CIT_WRITE) ||
1153-
(iot == CIT_READ && (file->f_flags & O_DIRECT))) &&
1154-
!(vio->vui_fd->fd_flags & LL_FILE_GROUP_LOCKED)) {
1155-
CDEBUG(D_VFSTRACE, "Range lock [%llu, %llu]\n",
1156-
range.rl_node.in_extent.start,
1157-
range.rl_node.in_extent.end);
1158-
result = range_lock(&lli->lli_write_tree,
1159-
&range);
1160-
if (result < 0)
1161-
goto out;
1162-
1163-
range_locked = true;
1164-
}
1165-
down_read(&lli->lli_trunc_sem);
1166-
break;
1167-
case IO_SPLICE:
1168-
vio->u.splice.vui_pipe = args->u.splice.via_pipe;
1169-
vio->u.splice.vui_flags = args->u.splice.via_flags;
1170-
break;
1171-
default:
1172-
CERROR("Unknown IO type - %u\n", vio->vui_io_subtype);
1173-
LBUG();
1159+
range_locked = true;
11741160
}
1161+
down_read(&lli->lli_trunc_sem);
11751162
ll_cl_add(file, env, io);
11761163
result = cl_io_loop(env, io);
11771164
ll_cl_remove(file, env);
1178-
if (args->via_io_subtype == IO_NORMAL)
1179-
up_read(&lli->lli_trunc_sem);
1165+
up_read(&lli->lli_trunc_sem);
11801166
if (range_locked) {
11811167
CDEBUG(D_VFSTRACE, "Range unlock [%llu, %llu]\n",
11821168
range.rl_node.in_extent.start,
@@ -1235,7 +1221,7 @@ static ssize_t ll_file_read_iter(struct kiocb *iocb, struct iov_iter *to)
12351221
if (IS_ERR(env))
12361222
return PTR_ERR(env);
12371223

1238-
args = ll_env_args(env, IO_NORMAL);
1224+
args = ll_env_args(env);
12391225
args->u.normal.via_iter = to;
12401226
args->u.normal.via_iocb = iocb;
12411227

@@ -1259,7 +1245,7 @@ static ssize_t ll_file_write_iter(struct kiocb *iocb, struct iov_iter *from)
12591245
if (IS_ERR(env))
12601246
return PTR_ERR(env);
12611247

1262-
args = ll_env_args(env, IO_NORMAL);
1248+
args = ll_env_args(env);
12631249
args->u.normal.via_iter = from;
12641250
args->u.normal.via_iocb = iocb;
12651251

@@ -1269,31 +1255,6 @@ static ssize_t ll_file_write_iter(struct kiocb *iocb, struct iov_iter *from)
12691255
return result;
12701256
}
12711257

1272-
/*
1273-
* Send file content (through pagecache) somewhere with helper
1274-
*/
1275-
static ssize_t ll_file_splice_read(struct file *in_file, loff_t *ppos,
1276-
struct pipe_inode_info *pipe, size_t count,
1277-
unsigned int flags)
1278-
{
1279-
struct lu_env *env;
1280-
struct vvp_io_args *args;
1281-
ssize_t result;
1282-
int refcheck;
1283-
1284-
env = cl_env_get(&refcheck);
1285-
if (IS_ERR(env))
1286-
return PTR_ERR(env);
1287-
1288-
args = ll_env_args(env, IO_SPLICE);
1289-
args->u.splice.via_pipe = pipe;
1290-
args->u.splice.via_flags = flags;
1291-
1292-
result = ll_file_io_generic(env, args, in_file, CIT_READ, ppos, count);
1293-
cl_env_put(env, &refcheck);
1294-
return result;
1295-
}
1296-
12971258
int ll_lov_setstripe_ea_info(struct inode *inode, struct dentry *dentry,
12981259
__u64 flags, struct lov_user_md *lum,
12991260
int lum_size)
@@ -3267,7 +3228,7 @@ struct file_operations ll_file_operations = {
32673228
.release = ll_file_release,
32683229
.mmap = ll_file_mmap,
32693230
.llseek = ll_file_seek,
3270-
.splice_read = ll_file_splice_read,
3231+
.splice_read = generic_file_splice_read,
32713232
.fsync = ll_fsync,
32723233
.flush = ll_flush
32733234
};
@@ -3280,7 +3241,7 @@ struct file_operations ll_file_operations_flock = {
32803241
.release = ll_file_release,
32813242
.mmap = ll_file_mmap,
32823243
.llseek = ll_file_seek,
3283-
.splice_read = ll_file_splice_read,
3244+
.splice_read = generic_file_splice_read,
32843245
.fsync = ll_fsync,
32853246
.flush = ll_flush,
32863247
.flock = ll_file_flock,
@@ -3296,7 +3257,7 @@ struct file_operations ll_file_operations_noflock = {
32963257
.release = ll_file_release,
32973258
.mmap = ll_file_mmap,
32983259
.llseek = ll_file_seek,
3299-
.splice_read = ll_file_splice_read,
3260+
.splice_read = generic_file_splice_read,
33003261
.fsync = ll_fsync,
33013262
.flush = ll_flush,
33023263
.flock = ll_file_noflock,

Diff for: drivers/staging/lustre/lustre/llite/llite_internal.h

+2-13
Original file line numberDiff line numberDiff line change
@@ -908,17 +908,11 @@ void vvp_write_complete(struct vvp_object *club, struct vvp_page *page);
908908
*/
909909
struct vvp_io_args {
910910
/** normal/splice */
911-
enum vvp_io_subtype via_io_subtype;
912-
913911
union {
914912
struct {
915913
struct kiocb *via_iocb;
916914
struct iov_iter *via_iter;
917915
} normal;
918-
struct {
919-
struct pipe_inode_info *via_pipe;
920-
unsigned int via_flags;
921-
} splice;
922916
} u;
923917
};
924918

@@ -946,14 +940,9 @@ static inline struct ll_thread_info *ll_env_info(const struct lu_env *env)
946940
return lti;
947941
}
948942

949-
static inline struct vvp_io_args *ll_env_args(const struct lu_env *env,
950-
enum vvp_io_subtype type)
943+
static inline struct vvp_io_args *ll_env_args(const struct lu_env *env)
951944
{
952-
struct vvp_io_args *via = &ll_env_info(env)->lti_args;
953-
954-
via->via_io_subtype = type;
955-
956-
return via;
945+
return &ll_env_info(env)->lti_args;
957946
}
958947

959948
void ll_queue_done_writing(struct inode *inode, unsigned long flags);

Diff for: drivers/staging/lustre/lustre/llite/vvp_internal.h

-14
Original file line numberDiff line numberDiff line change
@@ -49,14 +49,6 @@ struct obd_device;
4949
struct obd_export;
5050
struct page;
5151

52-
/* specific architecture can implement only part of this list */
53-
enum vvp_io_subtype {
54-
/** normal IO */
55-
IO_NORMAL,
56-
/** io started from splice_{read|write} */
57-
IO_SPLICE
58-
};
59-
6052
/**
6153
* IO state private to IO state private to VVP layer.
6254
*/
@@ -98,10 +90,6 @@ struct vvp_io {
9890
*/
9991
bool ft_flags_valid;
10092
} fault;
101-
struct {
102-
struct pipe_inode_info *vui_pipe;
103-
unsigned int vui_flags;
104-
} splice;
10593
struct {
10694
struct cl_page_list vui_queue;
10795
unsigned long vui_written;
@@ -110,8 +98,6 @@ struct vvp_io {
11098
} write;
11199
} u;
112100

113-
enum vvp_io_subtype vui_io_subtype;
114-
115101
/**
116102
* Layout version when this IO is initialized
117103
*/

Diff for: drivers/staging/lustre/lustre/llite/vvp_io.c

+4-41
Original file line numberDiff line numberDiff line change
@@ -53,18 +53,6 @@ static struct vvp_io *cl2vvp_io(const struct lu_env *env,
5353
return vio;
5454
}
5555

56-
/**
57-
* True, if \a io is a normal io, False for splice_{read,write}
58-
*/
59-
static int cl_is_normalio(const struct lu_env *env, const struct cl_io *io)
60-
{
61-
struct vvp_io *vio = vvp_env_io(env);
62-
63-
LASSERT(io->ci_type == CIT_READ || io->ci_type == CIT_WRITE);
64-
65-
return vio->vui_io_subtype == IO_NORMAL;
66-
}
67-
6856
/**
6957
* For swapping layout. The file's layout may have changed.
7058
* To avoid populating pages to a wrong stripe, we have to verify the
@@ -390,9 +378,6 @@ static int vvp_mmap_locks(const struct lu_env *env,
390378

391379
LASSERT(io->ci_type == CIT_READ || io->ci_type == CIT_WRITE);
392380

393-
if (!cl_is_normalio(env, io))
394-
return 0;
395-
396381
if (!vio->vui_iter) /* nfs or loop back device write */
397382
return 0;
398383

@@ -461,15 +446,10 @@ static void vvp_io_advance(const struct lu_env *env,
461446
const struct cl_io_slice *ios,
462447
size_t nob)
463448
{
464-
struct vvp_io *vio = cl2vvp_io(env, ios);
465-
struct cl_io *io = ios->cis_io;
466449
struct cl_object *obj = ios->cis_io->ci_obj;
467-
450+
struct vvp_io *vio = cl2vvp_io(env, ios);
468451
CLOBINVRNT(env, obj, vvp_object_invariant(obj));
469452

470-
if (!cl_is_normalio(env, io))
471-
return;
472-
473453
iov_iter_reexpand(vio->vui_iter, vio->vui_tot_count -= nob);
474454
}
475455

@@ -478,7 +458,7 @@ static void vvp_io_update_iov(const struct lu_env *env,
478458
{
479459
size_t size = io->u.ci_rw.crw_count;
480460

481-
if (!cl_is_normalio(env, io) || !vio->vui_iter)
461+
if (!vio->vui_iter)
482462
return;
483463

484464
iov_iter_truncate(vio->vui_iter, size);
@@ -715,25 +695,8 @@ static int vvp_io_read_start(const struct lu_env *env,
715695

716696
/* BUG: 5972 */
717697
file_accessed(file);
718-
switch (vio->vui_io_subtype) {
719-
case IO_NORMAL:
720-
LASSERT(vio->vui_iocb->ki_pos == pos);
721-
result = generic_file_read_iter(vio->vui_iocb, vio->vui_iter);
722-
break;
723-
case IO_SPLICE:
724-
result = generic_file_splice_read(file, &pos,
725-
vio->u.splice.vui_pipe, cnt,
726-
vio->u.splice.vui_flags);
727-
/* LU-1109: do splice read stripe by stripe otherwise if it
728-
* may make nfsd stuck if this read occupied all internal pipe
729-
* buffers.
730-
*/
731-
io->ci_continue = 0;
732-
break;
733-
default:
734-
CERROR("Wrong IO type %u\n", vio->vui_io_subtype);
735-
LBUG();
736-
}
698+
LASSERT(vio->vui_iocb->ki_pos == pos);
699+
result = generic_file_read_iter(vio->vui_iocb, vio->vui_iter);
737700

738701
out:
739702
if (result >= 0) {

Diff for: fs/coda/file.c

+1-22
Original file line numberDiff line numberDiff line change
@@ -37,27 +37,6 @@ coda_file_read_iter(struct kiocb *iocb, struct iov_iter *to)
3737
return vfs_iter_read(cfi->cfi_container, to, &iocb->ki_pos);
3838
}
3939

40-
static ssize_t
41-
coda_file_splice_read(struct file *coda_file, loff_t *ppos,
42-
struct pipe_inode_info *pipe, size_t count,
43-
unsigned int flags)
44-
{
45-
ssize_t (*splice_read)(struct file *, loff_t *,
46-
struct pipe_inode_info *, size_t, unsigned int);
47-
struct coda_file_info *cfi;
48-
struct file *host_file;
49-
50-
cfi = CODA_FTOC(coda_file);
51-
BUG_ON(!cfi || cfi->cfi_magic != CODA_MAGIC);
52-
host_file = cfi->cfi_container;
53-
54-
splice_read = host_file->f_op->splice_read;
55-
if (!splice_read)
56-
splice_read = default_file_splice_read;
57-
58-
return splice_read(host_file, ppos, pipe, count, flags);
59-
}
60-
6140
static ssize_t
6241
coda_file_write_iter(struct kiocb *iocb, struct iov_iter *to)
6342
{
@@ -225,6 +204,6 @@ const struct file_operations coda_file_operations = {
225204
.open = coda_open,
226205
.release = coda_release,
227206
.fsync = coda_fsync,
228-
.splice_read = coda_file_splice_read,
207+
.splice_read = generic_file_splice_read,
229208
};
230209

Diff for: fs/direct-io.c

+3
Original file line numberDiff line numberDiff line change
@@ -246,6 +246,9 @@ static ssize_t dio_complete(struct dio *dio, ssize_t ret, bool is_async)
246246
if ((dio->op == REQ_OP_READ) &&
247247
((offset + transferred) > dio->i_size))
248248
transferred = dio->i_size - offset;
249+
/* ignore EFAULT if some IO has been done */
250+
if (unlikely(ret == -EFAULT) && transferred)
251+
ret = 0;
249252
}
250253

251254
if (ret == 0)

0 commit comments

Comments
 (0)