Commit 2e02f9ef authored by Pavel Begunkov's avatar Pavel Begunkov Committed by Jens Axboe
Browse files

io_uring/rsrc: improve regbuf iov validation



Deduplicate io_buffer_validate() calls by moving the checks into
io_sqe_buffer_register(). Now we also don't need special handling in
io_buffer_validate() passing through buffer removal requests. I also
was using it as a cleanup before some other changes.

Signed-off-by: default avatarPavel Begunkov <asml.silence@gmail.com>
Signed-off-by: default avatarJens Axboe <axboe@kernel.dk>
parent 046fcc83
Loading
Loading
Loading
Loading
+10 −21
Original line number Diff line number Diff line
@@ -96,20 +96,6 @@ int io_validate_user_buf_range(u64 uaddr, u64 ulen)
	return 0;
}

static int io_buffer_validate(struct iovec *iov)
{
	/*
	 * Don't impose further limits on the size and buffer
	 * constraints here, we'll -EINVAL later when IO is
	 * submitted if they are wrong.
	 */
	if (!iov->iov_base)
		return iov->iov_len ? -EFAULT : 0;

	return io_validate_user_buf_range((unsigned long)iov->iov_base,
					  iov->iov_len);
}

static void io_release_ubuf(void *priv)
{
	struct io_mapped_ubuf *imu = priv;
@@ -319,9 +305,6 @@ static int __io_sqe_buffers_update(struct io_ring_ctx *ctx,
			err = -EFAULT;
			break;
		}
		err = io_buffer_validate(iov);
		if (err)
			break;
		node = io_sqe_buffer_register(ctx, iov, &last_hpage);
		if (IS_ERR(node)) {
			err = PTR_ERR(node);
@@ -790,8 +773,17 @@ static struct io_rsrc_node *io_sqe_buffer_register(struct io_ring_ctx *ctx,
	struct io_imu_folio_data data;
	bool coalesced = false;

	if (!iov->iov_base)
	if (!iov->iov_base) {
		if (iov->iov_len)
			return ERR_PTR(-EFAULT);
		/* remove the buffer without installing a new one */
		return NULL;
	}

	ret = io_validate_user_buf_range((unsigned long)iov->iov_base,
					 iov->iov_len);
	if (ret)
		return ERR_PTR(ret);

	node = io_rsrc_node_alloc(ctx, IORING_RSRC_BUFFER);
	if (!node)
@@ -897,9 +889,6 @@ int io_sqe_buffers_register(struct io_ring_ctx *ctx, void __user *arg,
				ret = PTR_ERR(iov);
				break;
			}
			ret = io_buffer_validate(iov);
			if (ret)
				break;
			if (ctx->compat)
				arg += sizeof(struct compat_iovec);
			else