mirror of
https://github.com/torvalds/linux.git
synced 2026-11-06 21:58:01 +01:00
net: Remove support for AIO on sockets
The only user of msg->msg_iocb was AF_ALG, but that's deprecated. It can be removed entirely at the cost of only supporting synchronous operations. This doesn't break userspace, which will silently block (for a bounded amount of time) in io_submit instead of operating asynchronously. This also makes struct msghdr smaller, helping every other caller of sendmsg(). Signed-off-by: Demi Marie Obenour <demiobenour@gmail.com> Acked-by: Jakub Kicinski <kuba@kernel.org> Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>
This commit is contained in:
parent
4c600ab0d8
commit
fcc77d33a3
|
|
@ -1085,35 +1085,6 @@ void af_alg_free_resources(struct af_alg_async_req *areq)
|
||||||
}
|
}
|
||||||
EXPORT_SYMBOL_GPL(af_alg_free_resources);
|
EXPORT_SYMBOL_GPL(af_alg_free_resources);
|
||||||
|
|
||||||
/**
|
|
||||||
* af_alg_async_cb - AIO callback handler
|
|
||||||
* @data: async request completion data
|
|
||||||
* @err: if non-zero, error result to be returned via ki_complete();
|
|
||||||
* otherwise return the AIO output length via ki_complete().
|
|
||||||
*
|
|
||||||
* This handler cleans up the struct af_alg_async_req upon completion of the
|
|
||||||
* AIO operation.
|
|
||||||
*
|
|
||||||
* The number of bytes to be generated with the AIO operation must be set
|
|
||||||
* in areq->outlen before the AIO callback handler is invoked.
|
|
||||||
*/
|
|
||||||
void af_alg_async_cb(void *data, int err)
|
|
||||||
{
|
|
||||||
struct af_alg_async_req *areq = data;
|
|
||||||
struct sock *sk = areq->sk;
|
|
||||||
struct kiocb *iocb = areq->iocb;
|
|
||||||
unsigned int resultlen;
|
|
||||||
|
|
||||||
/* Buffer size written by crypto operation. */
|
|
||||||
resultlen = areq->outlen;
|
|
||||||
|
|
||||||
af_alg_free_resources(areq);
|
|
||||||
sock_put(sk);
|
|
||||||
|
|
||||||
iocb->ki_complete(iocb, err ? err : (int)resultlen);
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(af_alg_async_cb);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* af_alg_poll - poll system call handler
|
* af_alg_poll - poll system call handler
|
||||||
* @file: file pointer
|
* @file: file pointer
|
||||||
|
|
@ -1154,8 +1125,8 @@ struct af_alg_async_req *af_alg_alloc_areq(struct sock *sk,
|
||||||
struct af_alg_ctx *ctx = alg_sk(sk)->private;
|
struct af_alg_ctx *ctx = alg_sk(sk)->private;
|
||||||
struct af_alg_async_req *areq;
|
struct af_alg_async_req *areq;
|
||||||
|
|
||||||
/* Only one AIO request can be in flight. */
|
/* Only one request can be in flight. */
|
||||||
if (ctx->inflight)
|
if (WARN_ON_ONCE(ctx->inflight))
|
||||||
return ERR_PTR(-EBUSY);
|
return ERR_PTR(-EBUSY);
|
||||||
|
|
||||||
areq = sock_kmalloc(sk, areqlen, GFP_KERNEL);
|
areq = sock_kmalloc(sk, areqlen, GFP_KERNEL);
|
||||||
|
|
|
||||||
|
|
@ -197,37 +197,14 @@ static int _aead_recvmsg(struct socket *sock, struct msghdr *msg,
|
||||||
aead_request_set_ad(&areq->cra_u.aead_req, ctx->aead_assoclen);
|
aead_request_set_ad(&areq->cra_u.aead_req, ctx->aead_assoclen);
|
||||||
aead_request_set_tfm(&areq->cra_u.aead_req, tfm);
|
aead_request_set_tfm(&areq->cra_u.aead_req, tfm);
|
||||||
|
|
||||||
if (msg->msg_iocb && !is_sync_kiocb(msg->msg_iocb)) {
|
aead_request_set_callback(&areq->cra_u.aead_req,
|
||||||
/* AIO operation */
|
CRYPTO_TFM_REQ_MAY_SLEEP |
|
||||||
sock_hold(sk);
|
CRYPTO_TFM_REQ_MAY_BACKLOG,
|
||||||
areq->iocb = msg->msg_iocb;
|
crypto_req_done, &ctx->wait);
|
||||||
|
err = crypto_wait_req(ctx->enc ?
|
||||||
/* Remember output size that will be generated. */
|
crypto_aead_encrypt(&areq->cra_u.aead_req) :
|
||||||
areq->outlen = outlen;
|
crypto_aead_decrypt(&areq->cra_u.aead_req),
|
||||||
|
&ctx->wait);
|
||||||
aead_request_set_callback(&areq->cra_u.aead_req,
|
|
||||||
CRYPTO_TFM_REQ_MAY_SLEEP,
|
|
||||||
af_alg_async_cb, areq);
|
|
||||||
err = ctx->enc ? crypto_aead_encrypt(&areq->cra_u.aead_req) :
|
|
||||||
crypto_aead_decrypt(&areq->cra_u.aead_req);
|
|
||||||
|
|
||||||
/* AIO operation in progress */
|
|
||||||
if (err == -EINPROGRESS)
|
|
||||||
return -EIOCBQUEUED;
|
|
||||||
|
|
||||||
sock_put(sk);
|
|
||||||
} else {
|
|
||||||
/* Synchronous operation */
|
|
||||||
aead_request_set_callback(&areq->cra_u.aead_req,
|
|
||||||
CRYPTO_TFM_REQ_MAY_SLEEP |
|
|
||||||
CRYPTO_TFM_REQ_MAY_BACKLOG,
|
|
||||||
crypto_req_done, &ctx->wait);
|
|
||||||
err = crypto_wait_req(ctx->enc ?
|
|
||||||
crypto_aead_encrypt(&areq->cra_u.aead_req) :
|
|
||||||
crypto_aead_decrypt(&areq->cra_u.aead_req),
|
|
||||||
&ctx->wait);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
free:
|
free:
|
||||||
af_alg_free_resources(areq);
|
af_alg_free_resources(areq);
|
||||||
|
|
|
||||||
|
|
@ -79,20 +79,6 @@ static int algif_skcipher_export(struct sock *sk, struct skcipher_request *req)
|
||||||
return err;
|
return err;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void algif_skcipher_done(void *data, int err)
|
|
||||||
{
|
|
||||||
struct af_alg_async_req *areq = data;
|
|
||||||
struct sock *sk = areq->sk;
|
|
||||||
|
|
||||||
if (err)
|
|
||||||
goto out;
|
|
||||||
|
|
||||||
err = algif_skcipher_export(sk, &areq->cra_u.skcipher_req);
|
|
||||||
|
|
||||||
out:
|
|
||||||
af_alg_async_cb(data, err);
|
|
||||||
}
|
|
||||||
|
|
||||||
static int _skcipher_recvmsg(struct socket *sock, struct msghdr *msg,
|
static int _skcipher_recvmsg(struct socket *sock, struct msghdr *msg,
|
||||||
size_t ignored, int flags)
|
size_t ignored, int flags)
|
||||||
{
|
{
|
||||||
|
|
@ -171,43 +157,19 @@ static int _skcipher_recvmsg(struct socket *sock, struct msghdr *msg,
|
||||||
cflags |= CRYPTO_SKCIPHER_REQ_CONT;
|
cflags |= CRYPTO_SKCIPHER_REQ_CONT;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (msg->msg_iocb && !is_sync_kiocb(msg->msg_iocb)) {
|
skcipher_request_set_callback(&areq->cra_u.skcipher_req,
|
||||||
/* AIO operation */
|
cflags |
|
||||||
sock_hold(sk);
|
CRYPTO_TFM_REQ_MAY_SLEEP |
|
||||||
areq->iocb = msg->msg_iocb;
|
CRYPTO_TFM_REQ_MAY_BACKLOG,
|
||||||
|
crypto_req_done, &ctx->wait);
|
||||||
|
err = crypto_wait_req(ctx->enc ?
|
||||||
|
crypto_skcipher_encrypt(&areq->cra_u.skcipher_req) :
|
||||||
|
crypto_skcipher_decrypt(&areq->cra_u.skcipher_req),
|
||||||
|
&ctx->wait);
|
||||||
|
|
||||||
/* Remember output size that will be generated. */
|
if (!err)
|
||||||
areq->outlen = len;
|
err = algif_skcipher_export(
|
||||||
|
sk, &areq->cra_u.skcipher_req);
|
||||||
skcipher_request_set_callback(&areq->cra_u.skcipher_req,
|
|
||||||
cflags |
|
|
||||||
CRYPTO_TFM_REQ_MAY_SLEEP,
|
|
||||||
algif_skcipher_done, areq);
|
|
||||||
err = ctx->enc ?
|
|
||||||
crypto_skcipher_encrypt(&areq->cra_u.skcipher_req) :
|
|
||||||
crypto_skcipher_decrypt(&areq->cra_u.skcipher_req);
|
|
||||||
|
|
||||||
/* AIO operation in progress */
|
|
||||||
if (err == -EINPROGRESS)
|
|
||||||
return -EIOCBQUEUED;
|
|
||||||
|
|
||||||
sock_put(sk);
|
|
||||||
} else {
|
|
||||||
/* Synchronous operation */
|
|
||||||
skcipher_request_set_callback(&areq->cra_u.skcipher_req,
|
|
||||||
cflags |
|
|
||||||
CRYPTO_TFM_REQ_MAY_SLEEP |
|
|
||||||
CRYPTO_TFM_REQ_MAY_BACKLOG,
|
|
||||||
crypto_req_done, &ctx->wait);
|
|
||||||
err = crypto_wait_req(ctx->enc ?
|
|
||||||
crypto_skcipher_encrypt(&areq->cra_u.skcipher_req) :
|
|
||||||
crypto_skcipher_decrypt(&areq->cra_u.skcipher_req),
|
|
||||||
&ctx->wait);
|
|
||||||
|
|
||||||
if (!err)
|
|
||||||
err = algif_skcipher_export(
|
|
||||||
sk, &areq->cra_u.skcipher_req);
|
|
||||||
}
|
|
||||||
|
|
||||||
free:
|
free:
|
||||||
af_alg_free_resources(areq);
|
af_alg_free_resources(areq);
|
||||||
|
|
|
||||||
|
|
@ -80,7 +80,6 @@ struct af_alg_rsgl {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* struct af_alg_async_req - definition of crypto request
|
* struct af_alg_async_req - definition of crypto request
|
||||||
* @iocb: IOCB for AIO operations
|
|
||||||
* @sk: Socket the request is associated with
|
* @sk: Socket the request is associated with
|
||||||
* @first_rsgl: First RX SG
|
* @first_rsgl: First RX SG
|
||||||
* @last_rsgl: Pointer to last RX SG
|
* @last_rsgl: Pointer to last RX SG
|
||||||
|
|
@ -92,7 +91,6 @@ struct af_alg_rsgl {
|
||||||
* @cra_u: Cipher request
|
* @cra_u: Cipher request
|
||||||
*/
|
*/
|
||||||
struct af_alg_async_req {
|
struct af_alg_async_req {
|
||||||
struct kiocb *iocb;
|
|
||||||
struct sock *sk;
|
struct sock *sk;
|
||||||
|
|
||||||
struct af_alg_rsgl first_rsgl;
|
struct af_alg_rsgl first_rsgl;
|
||||||
|
|
@ -138,7 +136,7 @@ struct af_alg_async_req {
|
||||||
* @write: True if we are in the middle of a write.
|
* @write: True if we are in the middle of a write.
|
||||||
* @init: True if metadata has been sent.
|
* @init: True if metadata has been sent.
|
||||||
* @len: Length of memory allocated for this data structure.
|
* @len: Length of memory allocated for this data structure.
|
||||||
* @inflight: Non-zero when AIO requests are in flight.
|
* @inflight: Non-zero when requests are in flight, for debugging only.
|
||||||
*/
|
*/
|
||||||
struct af_alg_ctx {
|
struct af_alg_ctx {
|
||||||
struct list_head tsgl_list;
|
struct list_head tsgl_list;
|
||||||
|
|
@ -237,7 +235,6 @@ int af_alg_wait_for_data(struct sock *sk, unsigned flags, unsigned min);
|
||||||
int af_alg_sendmsg(struct socket *sock, struct msghdr *msg, size_t size,
|
int af_alg_sendmsg(struct socket *sock, struct msghdr *msg, size_t size,
|
||||||
unsigned int ivsize);
|
unsigned int ivsize);
|
||||||
void af_alg_free_resources(struct af_alg_async_req *areq);
|
void af_alg_free_resources(struct af_alg_async_req *areq);
|
||||||
void af_alg_async_cb(void *data, int err);
|
|
||||||
__poll_t af_alg_poll(struct file *file, struct socket *sock,
|
__poll_t af_alg_poll(struct file *file, struct socket *sock,
|
||||||
poll_table *wait);
|
poll_table *wait);
|
||||||
struct af_alg_async_req *af_alg_alloc_areq(struct sock *sk,
|
struct af_alg_async_req *af_alg_alloc_areq(struct sock *sk,
|
||||||
|
|
|
||||||
|
|
@ -89,7 +89,6 @@ struct msghdr {
|
||||||
bool msg_get_inq : 1;/* return INQ after receive */
|
bool msg_get_inq : 1;/* return INQ after receive */
|
||||||
unsigned int msg_flags; /* flags on received message */
|
unsigned int msg_flags; /* flags on received message */
|
||||||
__kernel_size_t msg_controllen; /* ancillary data buffer length */
|
__kernel_size_t msg_controllen; /* ancillary data buffer length */
|
||||||
struct kiocb *msg_iocb; /* ptr to iocb for async requests */
|
|
||||||
struct ubuf_info *msg_ubuf;
|
struct ubuf_info *msg_ubuf;
|
||||||
int (*sg_from_iter)(struct sk_buff *skb,
|
int (*sg_from_iter)(struct sk_buff *skb,
|
||||||
struct iov_iter *from, size_t length);
|
struct iov_iter *from, size_t length);
|
||||||
|
|
|
||||||
|
|
@ -771,7 +771,6 @@ static int io_recvmsg_prep_setup(struct io_kiocb *req)
|
||||||
kmsg->msg.msg_control = NULL;
|
kmsg->msg.msg_control = NULL;
|
||||||
kmsg->msg.msg_get_inq = 1;
|
kmsg->msg.msg_get_inq = 1;
|
||||||
kmsg->msg.msg_controllen = 0;
|
kmsg->msg.msg_controllen = 0;
|
||||||
kmsg->msg.msg_iocb = NULL;
|
|
||||||
kmsg->msg.msg_ubuf = NULL;
|
kmsg->msg.msg_ubuf = NULL;
|
||||||
|
|
||||||
if (req->flags & REQ_F_BUFFER_SELECT)
|
if (req->flags & REQ_F_BUFFER_SELECT)
|
||||||
|
|
|
||||||
|
|
@ -75,7 +75,6 @@ int __get_compat_msghdr(struct msghdr *kmsg,
|
||||||
if (msg->msg_iovlen > UIO_MAXIOV)
|
if (msg->msg_iovlen > UIO_MAXIOV)
|
||||||
return -EMSGSIZE;
|
return -EMSGSIZE;
|
||||||
|
|
||||||
kmsg->msg_iocb = NULL;
|
|
||||||
kmsg->msg_ubuf = NULL;
|
kmsg->msg_ubuf = NULL;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1213,8 +1213,7 @@ static ssize_t sock_read_iter(struct kiocb *iocb, struct iov_iter *to)
|
||||||
{
|
{
|
||||||
struct file *file = iocb->ki_filp;
|
struct file *file = iocb->ki_filp;
|
||||||
struct socket *sock = file->private_data;
|
struct socket *sock = file->private_data;
|
||||||
struct msghdr msg = {.msg_iter = *to,
|
struct msghdr msg = {.msg_iter = *to};
|
||||||
.msg_iocb = iocb};
|
|
||||||
ssize_t res;
|
ssize_t res;
|
||||||
|
|
||||||
if (file->f_flags & O_NONBLOCK || (iocb->ki_flags & IOCB_NOWAIT))
|
if (file->f_flags & O_NONBLOCK || (iocb->ki_flags & IOCB_NOWAIT))
|
||||||
|
|
@ -1235,8 +1234,7 @@ static ssize_t sock_write_iter(struct kiocb *iocb, struct iov_iter *from)
|
||||||
{
|
{
|
||||||
struct file *file = iocb->ki_filp;
|
struct file *file = iocb->ki_filp;
|
||||||
struct socket *sock = file->private_data;
|
struct socket *sock = file->private_data;
|
||||||
struct msghdr msg = {.msg_iter = *from,
|
struct msghdr msg = {.msg_iter = *from};
|
||||||
.msg_iocb = iocb};
|
|
||||||
ssize_t res;
|
ssize_t res;
|
||||||
|
|
||||||
if (iocb->ki_pos != 0)
|
if (iocb->ki_pos != 0)
|
||||||
|
|
@ -2612,7 +2610,6 @@ int __copy_msghdr(struct msghdr *kmsg,
|
||||||
if (msg->msg_iovlen > UIO_MAXIOV)
|
if (msg->msg_iovlen > UIO_MAXIOV)
|
||||||
return -EMSGSIZE;
|
return -EMSGSIZE;
|
||||||
|
|
||||||
kmsg->msg_iocb = NULL;
|
|
||||||
kmsg->msg_ubuf = NULL;
|
kmsg->msg_ubuf = NULL;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -89,7 +89,6 @@ struct msghdr {
|
||||||
bool msg_get_inq : 1;/* return INQ after receive */
|
bool msg_get_inq : 1;/* return INQ after receive */
|
||||||
unsigned int msg_flags; /* flags on received message */
|
unsigned int msg_flags; /* flags on received message */
|
||||||
__kernel_size_t msg_controllen; /* ancillary data buffer length */
|
__kernel_size_t msg_controllen; /* ancillary data buffer length */
|
||||||
struct kiocb *msg_iocb; /* ptr to iocb for async requests */
|
|
||||||
struct ubuf_info *msg_ubuf;
|
struct ubuf_info *msg_ubuf;
|
||||||
int (*sg_from_iter)(struct sk_buff *skb,
|
int (*sg_from_iter)(struct sk_buff *skb,
|
||||||
struct iov_iter *from, size_t length);
|
struct iov_iter *from, size_t length);
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user