forked from mirrors/linux
		
	crypto: af_alg: Support MSG_SPLICE_PAGES
Make AF_ALG sendmsg() support MSG_SPLICE_PAGES. This causes pages to be spliced from the source iterator. This allows ->sendpage() to be replaced by something that can handle multiple multipage folios in a single transaction. Signed-off-by: David Howells <dhowells@redhat.com> cc: Herbert Xu <herbert@gondor.apana.org.au> cc: "David S. Miller" <davem@davemloft.net> cc: Eric Dumazet <edumazet@google.com> cc: Jakub Kicinski <kuba@kernel.org> cc: Paolo Abeni <pabeni@redhat.com> cc: Jens Axboe <axboe@kernel.dk> cc: Matthew Wilcox <willy@infradead.org> cc: linux-crypto@vger.kernel.org cc: netdev@vger.kernel.org Acked-by: Herbert Xu <herbert@gondor.apana.org.au> Signed-off-by: Paolo Abeni <pabeni@redhat.com>
This commit is contained in:
		
							parent
							
								
									73d7409cfd
								
							
						
					
					
						commit
						bf63e250c4
					
				
					 3 changed files with 37 additions and 17 deletions
				
			
		|  | @ -985,7 +985,7 @@ int af_alg_sendmsg(struct socket *sock, struct msghdr *msg, size_t size, | ||||||
| 	while (size) { | 	while (size) { | ||||||
| 		struct scatterlist *sg; | 		struct scatterlist *sg; | ||||||
| 		size_t len = size; | 		size_t len = size; | ||||||
| 		size_t plen; | 		ssize_t plen; | ||||||
| 
 | 
 | ||||||
| 		/* use the existing memory in an allocated page */ | 		/* use the existing memory in an allocated page */ | ||||||
| 		if (ctx->merge) { | 		if (ctx->merge) { | ||||||
|  | @ -1030,7 +1030,27 @@ int af_alg_sendmsg(struct socket *sock, struct msghdr *msg, size_t size, | ||||||
| 		if (sgl->cur) | 		if (sgl->cur) | ||||||
| 			sg_unmark_end(sg + sgl->cur - 1); | 			sg_unmark_end(sg + sgl->cur - 1); | ||||||
| 
 | 
 | ||||||
| 		if (1 /* TODO check MSG_SPLICE_PAGES */) { | 		if (msg->msg_flags & MSG_SPLICE_PAGES) { | ||||||
|  | 			struct sg_table sgtable = { | ||||||
|  | 				.sgl		= sg, | ||||||
|  | 				.nents		= sgl->cur, | ||||||
|  | 				.orig_nents	= sgl->cur, | ||||||
|  | 			}; | ||||||
|  | 
 | ||||||
|  | 			plen = extract_iter_to_sg(&msg->msg_iter, len, &sgtable, | ||||||
|  | 						  MAX_SGL_ENTS, 0); | ||||||
|  | 			if (plen < 0) { | ||||||
|  | 				err = plen; | ||||||
|  | 				goto unlock; | ||||||
|  | 			} | ||||||
|  | 
 | ||||||
|  | 			for (; sgl->cur < sgtable.nents; sgl->cur++) | ||||||
|  | 				get_page(sg_page(&sg[sgl->cur])); | ||||||
|  | 			len -= plen; | ||||||
|  | 			ctx->used += plen; | ||||||
|  | 			copied += plen; | ||||||
|  | 			size -= plen; | ||||||
|  | 		} else { | ||||||
| 			do { | 			do { | ||||||
| 				struct page *pg; | 				struct page *pg; | ||||||
| 				unsigned int i = sgl->cur; | 				unsigned int i = sgl->cur; | ||||||
|  |  | ||||||
|  | @ -9,8 +9,8 @@ | ||||||
|  * The following concept of the memory management is used: |  * The following concept of the memory management is used: | ||||||
|  * |  * | ||||||
|  * The kernel maintains two SGLs, the TX SGL and the RX SGL. The TX SGL is |  * The kernel maintains two SGLs, the TX SGL and the RX SGL. The TX SGL is | ||||||
|  * filled by user space with the data submitted via sendpage/sendmsg. Filling |  * filled by user space with the data submitted via sendpage. Filling up | ||||||
|  * up the TX SGL does not cause a crypto operation -- the data will only be |  * the TX SGL does not cause a crypto operation -- the data will only be | ||||||
|  * tracked by the kernel. Upon receipt of one recvmsg call, the caller must |  * tracked by the kernel. Upon receipt of one recvmsg call, the caller must | ||||||
|  * provide a buffer which is tracked with the RX SGL. |  * provide a buffer which is tracked with the RX SGL. | ||||||
|  * |  * | ||||||
|  | @ -113,19 +113,19 @@ static int _aead_recvmsg(struct socket *sock, struct msghdr *msg, | ||||||
| 	} | 	} | ||||||
| 
 | 
 | ||||||
| 	/*
 | 	/*
 | ||||||
| 	 * Data length provided by caller via sendmsg/sendpage that has not | 	 * Data length provided by caller via sendmsg that has not yet been | ||||||
| 	 * yet been processed. | 	 * processed. | ||||||
| 	 */ | 	 */ | ||||||
| 	used = ctx->used; | 	used = ctx->used; | ||||||
| 
 | 
 | ||||||
| 	/*
 | 	/*
 | ||||||
| 	 * Make sure sufficient data is present -- note, the same check is | 	 * Make sure sufficient data is present -- note, the same check is also | ||||||
| 	 * also present in sendmsg/sendpage. The checks in sendpage/sendmsg | 	 * present in sendmsg. The checks in sendmsg shall provide an | ||||||
| 	 * shall provide an information to the data sender that something is | 	 * information to the data sender that something is wrong, but they are | ||||||
| 	 * wrong, but they are irrelevant to maintain the kernel integrity. | 	 * irrelevant to maintain the kernel integrity.  We need this check | ||||||
| 	 * We need this check here too in case user space decides to not honor | 	 * here too in case user space decides to not honor the error message | ||||||
| 	 * the error message in sendmsg/sendpage and still call recvmsg. This | 	 * in sendmsg and still call recvmsg. This check here protects the | ||||||
| 	 * check here protects the kernel integrity. | 	 * kernel integrity. | ||||||
| 	 */ | 	 */ | ||||||
| 	if (!aead_sufficient_data(sk)) | 	if (!aead_sufficient_data(sk)) | ||||||
| 		return -EINVAL; | 		return -EINVAL; | ||||||
|  |  | ||||||
|  | @ -9,10 +9,10 @@ | ||||||
|  * The following concept of the memory management is used: |  * The following concept of the memory management is used: | ||||||
|  * |  * | ||||||
|  * The kernel maintains two SGLs, the TX SGL and the RX SGL. The TX SGL is |  * The kernel maintains two SGLs, the TX SGL and the RX SGL. The TX SGL is | ||||||
|  * filled by user space with the data submitted via sendpage/sendmsg. Filling |  * filled by user space with the data submitted via sendmsg. Filling up the TX | ||||||
|  * up the TX SGL does not cause a crypto operation -- the data will only be |  * SGL does not cause a crypto operation -- the data will only be tracked by | ||||||
|  * tracked by the kernel. Upon receipt of one recvmsg call, the caller must |  * the kernel. Upon receipt of one recvmsg call, the caller must provide a | ||||||
|  * provide a buffer which is tracked with the RX SGL. |  * buffer which is tracked with the RX SGL. | ||||||
|  * |  * | ||||||
|  * During the processing of the recvmsg operation, the cipher request is |  * During the processing of the recvmsg operation, the cipher request is | ||||||
|  * allocated and prepared. As part of the recvmsg operation, the processed |  * allocated and prepared. As part of the recvmsg operation, the processed | ||||||
|  |  | ||||||
		Loading…
	
		Reference in a new issue
	
	 David Howells
						David Howells