* [PATCH v2 0/2] io_uring tee support
@ 2020-05-17 11:18 Pavel Begunkov
2020-05-17 11:18 ` [PATCH v2 1/2] splice: export do_tee() Pavel Begunkov
` (2 more replies)
0 siblings, 3 replies; 4+ messages in thread
From: Pavel Begunkov @ 2020-05-17 11:18 UTC (permalink / raw)
To: Jens Axboe, io-uring, linux-kernel
Add tee support.
v2: handle zero-len tee
Pavel Begunkov (2):
splice: export do_tee()
io_uring: add tee(2) support
fs/io_uring.c | 62 +++++++++++++++++++++++++++++++++--
fs/splice.c | 3 +-
include/linux/splice.h | 3 ++
include/uapi/linux/io_uring.h | 1 +
4 files changed, 64 insertions(+), 5 deletions(-)
--
2.24.0
^ permalink raw reply [flat|nested] 4+ messages in thread
* [PATCH v2 1/2] splice: export do_tee()
2020-05-17 11:18 [PATCH v2 0/2] io_uring tee support Pavel Begunkov
@ 2020-05-17 11:18 ` Pavel Begunkov
2020-05-17 11:18 ` [PATCH v2 2/2] io_uring: add tee(2) support Pavel Begunkov
2020-05-17 20:23 ` [PATCH v2 0/2] io_uring tee support Jens Axboe
2 siblings, 0 replies; 4+ messages in thread
From: Pavel Begunkov @ 2020-05-17 11:18 UTC (permalink / raw)
To: Jens Axboe, io-uring, linux-kernel
export do_tee() for use in io_uring
Signed-off-by: Pavel Begunkov <asml.silence@gmail.com>
---
fs/splice.c | 3 +--
include/linux/splice.h | 3 +++
2 files changed, 4 insertions(+), 2 deletions(-)
diff --git a/fs/splice.c b/fs/splice.c
index fd0a1e7e5959..a1dd54de24d8 100644
--- a/fs/splice.c
+++ b/fs/splice.c
@@ -1754,8 +1754,7 @@ static int link_pipe(struct pipe_inode_info *ipipe,
* The 'flags' used are the SPLICE_F_* variants, currently the only
* applicable one is SPLICE_F_NONBLOCK.
*/
-static long do_tee(struct file *in, struct file *out, size_t len,
- unsigned int flags)
+long do_tee(struct file *in, struct file *out, size_t len, unsigned int flags)
{
struct pipe_inode_info *ipipe = get_pipe_info(in);
struct pipe_inode_info *opipe = get_pipe_info(out);
diff --git a/include/linux/splice.h b/include/linux/splice.h
index ebbbfea48aa0..5c47013f708e 100644
--- a/include/linux/splice.h
+++ b/include/linux/splice.h
@@ -82,6 +82,9 @@ extern long do_splice(struct file *in, loff_t __user *off_in,
struct file *out, loff_t __user *off_out,
size_t len, unsigned int flags);
+extern long do_tee(struct file *in, struct file *out, size_t len,
+ unsigned int flags);
+
/*
* for dynamic pipe sizing
*/
--
2.24.0
^ permalink raw reply related [flat|nested] 4+ messages in thread
* [PATCH v2 2/2] io_uring: add tee(2) support
2020-05-17 11:18 [PATCH v2 0/2] io_uring tee support Pavel Begunkov
2020-05-17 11:18 ` [PATCH v2 1/2] splice: export do_tee() Pavel Begunkov
@ 2020-05-17 11:18 ` Pavel Begunkov
2020-05-17 20:23 ` [PATCH v2 0/2] io_uring tee support Jens Axboe
2 siblings, 0 replies; 4+ messages in thread
From: Pavel Begunkov @ 2020-05-17 11:18 UTC (permalink / raw)
To: Jens Axboe, io-uring, linux-kernel
Add IORING_OP_TEE implementing tee(2) support. Almost identical to
splice bits, but without offsets.
Signed-off-by: Pavel Begunkov <asml.silence@gmail.com>
---
fs/io_uring.c | 62 +++++++++++++++++++++++++++++++++--
include/uapi/linux/io_uring.h | 1 +
2 files changed, 60 insertions(+), 3 deletions(-)
diff --git a/fs/io_uring.c b/fs/io_uring.c
index 83b599815cf0..7f25e145a60a 100644
--- a/fs/io_uring.c
+++ b/fs/io_uring.c
@@ -853,6 +853,11 @@ static const struct io_op_def io_op_defs[] = {
},
[IORING_OP_PROVIDE_BUFFERS] = {},
[IORING_OP_REMOVE_BUFFERS] = {},
+ [IORING_OP_TEE] = {
+ .needs_file = 1,
+ .hash_reg_file = 1,
+ .unbound_nonreg_file = 1,
+ },
};
static void io_wq_submit_work(struct io_wq_work **workptr);
@@ -2748,7 +2753,8 @@ static int io_write(struct io_kiocb *req, bool force_nonblock)
return ret;
}
-static int io_splice_prep(struct io_kiocb *req, const struct io_uring_sqe *sqe)
+static int __io_splice_prep(struct io_kiocb *req,
+ const struct io_uring_sqe *sqe)
{
struct io_splice* sp = &req->splice;
unsigned int valid_flags = SPLICE_F_FD_IN_FIXED | SPLICE_F_ALL;
@@ -2758,8 +2764,6 @@ static int io_splice_prep(struct io_kiocb *req, const struct io_uring_sqe *sqe)
return 0;
sp->file_in = NULL;
- sp->off_in = READ_ONCE(sqe->splice_off_in);
- sp->off_out = READ_ONCE(sqe->off);
sp->len = READ_ONCE(sqe->len);
sp->flags = READ_ONCE(sqe->splice_flags);
@@ -2778,6 +2782,46 @@ static int io_splice_prep(struct io_kiocb *req, const struct io_uring_sqe *sqe)
return 0;
}
+static int io_tee_prep(struct io_kiocb *req,
+ const struct io_uring_sqe *sqe)
+{
+ if (READ_ONCE(sqe->splice_off_in) || READ_ONCE(sqe->off))
+ return -EINVAL;
+ return __io_splice_prep(req, sqe);
+}
+
+static int io_tee(struct io_kiocb *req, bool force_nonblock)
+{
+ struct io_splice *sp = &req->splice;
+ struct file *in = sp->file_in;
+ struct file *out = sp->file_out;
+ unsigned int flags = sp->flags & ~SPLICE_F_FD_IN_FIXED;
+ long ret = 0;
+
+ if (force_nonblock)
+ return -EAGAIN;
+ if (sp->len)
+ ret = do_tee(in, out, sp->len, flags);
+
+ io_put_file(req, in, (sp->flags & SPLICE_F_FD_IN_FIXED));
+ req->flags &= ~REQ_F_NEED_CLEANUP;
+
+ io_cqring_add_event(req, ret);
+ if (ret != sp->len)
+ req_set_fail_links(req);
+ io_put_req(req);
+ return 0;
+}
+
+static int io_splice_prep(struct io_kiocb *req, const struct io_uring_sqe *sqe)
+{
+ struct io_splice* sp = &req->splice;
+
+ sp->off_in = READ_ONCE(sqe->splice_off_in);
+ sp->off_out = READ_ONCE(sqe->off);
+ return __io_splice_prep(req, sqe);
+}
+
static int io_splice(struct io_kiocb *req, bool force_nonblock)
{
struct io_splice *sp = &req->splice;
@@ -5087,6 +5131,9 @@ static int io_req_defer_prep(struct io_kiocb *req,
case IORING_OP_REMOVE_BUFFERS:
ret = io_remove_buffers_prep(req, sqe);
break;
+ case IORING_OP_TEE:
+ ret = io_tee_prep(req, sqe);
+ break;
default:
printk_once(KERN_WARNING "io_uring: unhandled opcode %d\n",
req->opcode);
@@ -5161,6 +5208,7 @@ static void io_cleanup_req(struct io_kiocb *req)
putname(req->open.filename);
break;
case IORING_OP_SPLICE:
+ case IORING_OP_TEE:
io_put_file(req, req->splice.file_in,
(req->splice.flags & SPLICE_F_FD_IN_FIXED));
break;
@@ -5391,6 +5439,14 @@ static int io_issue_sqe(struct io_kiocb *req, const struct io_uring_sqe *sqe,
}
ret = io_remove_buffers(req, force_nonblock);
break;
+ case IORING_OP_TEE:
+ if (sqe) {
+ ret = io_tee_prep(req, sqe);
+ if (ret < 0)
+ break;
+ }
+ ret = io_tee(req, force_nonblock);
+ break;
default:
ret = -EINVAL;
break;
diff --git a/include/uapi/linux/io_uring.h b/include/uapi/linux/io_uring.h
index 8c5775df08b8..92c22699a5a7 100644
--- a/include/uapi/linux/io_uring.h
+++ b/include/uapi/linux/io_uring.h
@@ -129,6 +129,7 @@ enum {
IORING_OP_SPLICE,
IORING_OP_PROVIDE_BUFFERS,
IORING_OP_REMOVE_BUFFERS,
+ IORING_OP_TEE,
/* this goes last, obviously */
IORING_OP_LAST,
--
2.24.0
^ permalink raw reply related [flat|nested] 4+ messages in thread
* Re: [PATCH v2 0/2] io_uring tee support
2020-05-17 11:18 [PATCH v2 0/2] io_uring tee support Pavel Begunkov
2020-05-17 11:18 ` [PATCH v2 1/2] splice: export do_tee() Pavel Begunkov
2020-05-17 11:18 ` [PATCH v2 2/2] io_uring: add tee(2) support Pavel Begunkov
@ 2020-05-17 20:23 ` Jens Axboe
2 siblings, 0 replies; 4+ messages in thread
From: Jens Axboe @ 2020-05-17 20:23 UTC (permalink / raw)
To: Pavel Begunkov, io-uring, linux-kernel
On 5/17/20 5:18 AM, Pavel Begunkov wrote:
> Add tee support.
>
> v2: handle zero-len tee
>
> Pavel Begunkov (2):
> splice: export do_tee()
> io_uring: add tee(2) support
>
> fs/io_uring.c | 62 +++++++++++++++++++++++++++++++++--
> fs/splice.c | 3 +-
> include/linux/splice.h | 3 ++
> include/uapi/linux/io_uring.h | 1 +
> 4 files changed, 64 insertions(+), 5 deletions(-)
Applied, thanks.
--
Jens Axboe
^ permalink raw reply [flat|nested] 4+ messages in thread
end of thread, other threads:[~2020-05-17 20:23 UTC | newest]
Thread overview: 4+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2020-05-17 11:18 [PATCH v2 0/2] io_uring tee support Pavel Begunkov
2020-05-17 11:18 ` [PATCH v2 1/2] splice: export do_tee() Pavel Begunkov
2020-05-17 11:18 ` [PATCH v2 2/2] io_uring: add tee(2) support Pavel Begunkov
2020-05-17 20:23 ` [PATCH v2 0/2] io_uring tee support Jens Axboe
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.