forked from mirrors/linux
		
	net: add queue argument to __skb_wait_for_more_packets and __skb_{,try_}recv_datagram
This will be used by ESP over TCP to handle the queue of IKE messages. Signed-off-by: Sabrina Dubroca <sd@queasysnail.net> Acked-by: David S. Miller <davem@davemloft.net> Signed-off-by: Steffen Klassert <steffen.klassert@secunet.com>
This commit is contained in:
		
							parent
							
								
									e7096c131e
								
							
						
					
					
						commit
						b50b0580d2
					
				
					 4 changed files with 31 additions and 17 deletions
				
			
		|  | @ -3459,7 +3459,8 @@ static inline void skb_frag_list_init(struct sk_buff *skb) | ||||||
| 	for (iter = skb_shinfo(skb)->frag_list; iter; iter = iter->next) | 	for (iter = skb_shinfo(skb)->frag_list; iter; iter = iter->next) | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
| int __skb_wait_for_more_packets(struct sock *sk, int *err, long *timeo_p, | int __skb_wait_for_more_packets(struct sock *sk, struct sk_buff_head *queue, | ||||||
|  | 				int *err, long *timeo_p, | ||||||
| 				const struct sk_buff *skb); | 				const struct sk_buff *skb); | ||||||
| struct sk_buff *__skb_try_recv_from_queue(struct sock *sk, | struct sk_buff *__skb_try_recv_from_queue(struct sock *sk, | ||||||
| 					  struct sk_buff_head *queue, | 					  struct sk_buff_head *queue, | ||||||
|  | @ -3468,12 +3469,16 @@ struct sk_buff *__skb_try_recv_from_queue(struct sock *sk, | ||||||
| 							   struct sk_buff *skb), | 							   struct sk_buff *skb), | ||||||
| 					  int *off, int *err, | 					  int *off, int *err, | ||||||
| 					  struct sk_buff **last); | 					  struct sk_buff **last); | ||||||
| struct sk_buff *__skb_try_recv_datagram(struct sock *sk, unsigned flags, | struct sk_buff *__skb_try_recv_datagram(struct sock *sk, | ||||||
|  | 					struct sk_buff_head *queue, | ||||||
|  | 					unsigned int flags, | ||||||
| 					void (*destructor)(struct sock *sk, | 					void (*destructor)(struct sock *sk, | ||||||
| 							   struct sk_buff *skb), | 							   struct sk_buff *skb), | ||||||
| 					int *off, int *err, | 					int *off, int *err, | ||||||
| 					struct sk_buff **last); | 					struct sk_buff **last); | ||||||
| struct sk_buff *__skb_recv_datagram(struct sock *sk, unsigned flags, | struct sk_buff *__skb_recv_datagram(struct sock *sk, | ||||||
|  | 				    struct sk_buff_head *sk_queue, | ||||||
|  | 				    unsigned int flags, | ||||||
| 				    void (*destructor)(struct sock *sk, | 				    void (*destructor)(struct sock *sk, | ||||||
| 						       struct sk_buff *skb), | 						       struct sk_buff *skb), | ||||||
| 				    int *off, int *err); | 				    int *off, int *err); | ||||||
|  |  | ||||||
|  | @ -84,7 +84,8 @@ static int receiver_wake_function(wait_queue_entry_t *wait, unsigned int mode, i | ||||||
| /*
 | /*
 | ||||||
|  * Wait for the last received packet to be different from skb |  * Wait for the last received packet to be different from skb | ||||||
|  */ |  */ | ||||||
| int __skb_wait_for_more_packets(struct sock *sk, int *err, long *timeo_p, | int __skb_wait_for_more_packets(struct sock *sk, struct sk_buff_head *queue, | ||||||
|  | 				int *err, long *timeo_p, | ||||||
| 				const struct sk_buff *skb) | 				const struct sk_buff *skb) | ||||||
| { | { | ||||||
| 	int error; | 	int error; | ||||||
|  | @ -97,7 +98,7 @@ int __skb_wait_for_more_packets(struct sock *sk, int *err, long *timeo_p, | ||||||
| 	if (error) | 	if (error) | ||||||
| 		goto out_err; | 		goto out_err; | ||||||
| 
 | 
 | ||||||
| 	if (READ_ONCE(sk->sk_receive_queue.prev) != skb) | 	if (READ_ONCE(queue->prev) != skb) | ||||||
| 		goto out; | 		goto out; | ||||||
| 
 | 
 | ||||||
| 	/* Socket shut down? */ | 	/* Socket shut down? */ | ||||||
|  | @ -209,6 +210,7 @@ struct sk_buff *__skb_try_recv_from_queue(struct sock *sk, | ||||||
| /**
 | /**
 | ||||||
|  *	__skb_try_recv_datagram - Receive a datagram skbuff |  *	__skb_try_recv_datagram - Receive a datagram skbuff | ||||||
|  *	@sk: socket |  *	@sk: socket | ||||||
|  |  *	@queue: socket queue from which to receive | ||||||
|  *	@flags: MSG\_ flags |  *	@flags: MSG\_ flags | ||||||
|  *	@destructor: invoked under the receive lock on successful dequeue |  *	@destructor: invoked under the receive lock on successful dequeue | ||||||
|  *	@off: an offset in bytes to peek skb from. Returns an offset |  *	@off: an offset in bytes to peek skb from. Returns an offset | ||||||
|  | @ -241,13 +243,14 @@ struct sk_buff *__skb_try_recv_from_queue(struct sock *sk, | ||||||
|  *	quite explicitly by POSIX 1003.1g, don't change them without having |  *	quite explicitly by POSIX 1003.1g, don't change them without having | ||||||
|  *	the standard around please. |  *	the standard around please. | ||||||
|  */ |  */ | ||||||
| struct sk_buff *__skb_try_recv_datagram(struct sock *sk, unsigned int flags, | struct sk_buff *__skb_try_recv_datagram(struct sock *sk, | ||||||
|  | 					struct sk_buff_head *queue, | ||||||
|  | 					unsigned int flags, | ||||||
| 					void (*destructor)(struct sock *sk, | 					void (*destructor)(struct sock *sk, | ||||||
| 							   struct sk_buff *skb), | 							   struct sk_buff *skb), | ||||||
| 					int *off, int *err, | 					int *off, int *err, | ||||||
| 					struct sk_buff **last) | 					struct sk_buff **last) | ||||||
| { | { | ||||||
| 	struct sk_buff_head *queue = &sk->sk_receive_queue; |  | ||||||
| 	struct sk_buff *skb; | 	struct sk_buff *skb; | ||||||
| 	unsigned long cpu_flags; | 	unsigned long cpu_flags; | ||||||
| 	/*
 | 	/*
 | ||||||
|  | @ -278,7 +281,7 @@ struct sk_buff *__skb_try_recv_datagram(struct sock *sk, unsigned int flags, | ||||||
| 			break; | 			break; | ||||||
| 
 | 
 | ||||||
| 		sk_busy_loop(sk, flags & MSG_DONTWAIT); | 		sk_busy_loop(sk, flags & MSG_DONTWAIT); | ||||||
| 	} while (READ_ONCE(sk->sk_receive_queue.prev) != *last); | 	} while (READ_ONCE(queue->prev) != *last); | ||||||
| 
 | 
 | ||||||
| 	error = -EAGAIN; | 	error = -EAGAIN; | ||||||
| 
 | 
 | ||||||
|  | @ -288,7 +291,9 @@ struct sk_buff *__skb_try_recv_datagram(struct sock *sk, unsigned int flags, | ||||||
| } | } | ||||||
| EXPORT_SYMBOL(__skb_try_recv_datagram); | EXPORT_SYMBOL(__skb_try_recv_datagram); | ||||||
| 
 | 
 | ||||||
| struct sk_buff *__skb_recv_datagram(struct sock *sk, unsigned int flags, | struct sk_buff *__skb_recv_datagram(struct sock *sk, | ||||||
|  | 				    struct sk_buff_head *sk_queue, | ||||||
|  | 				    unsigned int flags, | ||||||
| 				    void (*destructor)(struct sock *sk, | 				    void (*destructor)(struct sock *sk, | ||||||
| 						       struct sk_buff *skb), | 						       struct sk_buff *skb), | ||||||
| 				    int *off, int *err) | 				    int *off, int *err) | ||||||
|  | @ -299,15 +304,16 @@ struct sk_buff *__skb_recv_datagram(struct sock *sk, unsigned int flags, | ||||||
| 	timeo = sock_rcvtimeo(sk, flags & MSG_DONTWAIT); | 	timeo = sock_rcvtimeo(sk, flags & MSG_DONTWAIT); | ||||||
| 
 | 
 | ||||||
| 	do { | 	do { | ||||||
| 		skb = __skb_try_recv_datagram(sk, flags, destructor, off, err, | 		skb = __skb_try_recv_datagram(sk, sk_queue, flags, destructor, | ||||||
| 					      &last); | 					      off, err, &last); | ||||||
| 		if (skb) | 		if (skb) | ||||||
| 			return skb; | 			return skb; | ||||||
| 
 | 
 | ||||||
| 		if (*err != -EAGAIN) | 		if (*err != -EAGAIN) | ||||||
| 			break; | 			break; | ||||||
| 	} while (timeo && | 	} while (timeo && | ||||||
| 		!__skb_wait_for_more_packets(sk, err, &timeo, last)); | 		 !__skb_wait_for_more_packets(sk, sk_queue, err, | ||||||
|  | 					      &timeo, last)); | ||||||
| 
 | 
 | ||||||
| 	return NULL; | 	return NULL; | ||||||
| } | } | ||||||
|  | @ -318,7 +324,8 @@ struct sk_buff *skb_recv_datagram(struct sock *sk, unsigned int flags, | ||||||
| { | { | ||||||
| 	int off = 0; | 	int off = 0; | ||||||
| 
 | 
 | ||||||
| 	return __skb_recv_datagram(sk, flags | (noblock ? MSG_DONTWAIT : 0), | 	return __skb_recv_datagram(sk, &sk->sk_receive_queue, | ||||||
|  | 				   flags | (noblock ? MSG_DONTWAIT : 0), | ||||||
| 				   NULL, &off, err); | 				   NULL, &off, err); | ||||||
| } | } | ||||||
| EXPORT_SYMBOL(skb_recv_datagram); | EXPORT_SYMBOL(skb_recv_datagram); | ||||||
|  |  | ||||||
|  | @ -1708,7 +1708,8 @@ struct sk_buff *__skb_recv_udp(struct sock *sk, unsigned int flags, | ||||||
| 
 | 
 | ||||||
| 		/* sk_queue is empty, reader_queue may contain peeked packets */ | 		/* sk_queue is empty, reader_queue may contain peeked packets */ | ||||||
| 	} while (timeo && | 	} while (timeo && | ||||||
| 		 !__skb_wait_for_more_packets(sk, &error, &timeo, | 		 !__skb_wait_for_more_packets(sk, &sk->sk_receive_queue, | ||||||
|  | 					      &error, &timeo, | ||||||
| 					      (struct sk_buff *)sk_queue)); | 					      (struct sk_buff *)sk_queue)); | ||||||
| 
 | 
 | ||||||
| 	*err = error; | 	*err = error; | ||||||
|  |  | ||||||
|  | @ -2058,8 +2058,8 @@ static int unix_dgram_recvmsg(struct socket *sock, struct msghdr *msg, | ||||||
| 		mutex_lock(&u->iolock); | 		mutex_lock(&u->iolock); | ||||||
| 
 | 
 | ||||||
| 		skip = sk_peek_offset(sk, flags); | 		skip = sk_peek_offset(sk, flags); | ||||||
| 		skb = __skb_try_recv_datagram(sk, flags, NULL, &skip, &err, | 		skb = __skb_try_recv_datagram(sk, &sk->sk_receive_queue, flags, | ||||||
| 					      &last); | 					      NULL, &skip, &err, &last); | ||||||
| 		if (skb) | 		if (skb) | ||||||
| 			break; | 			break; | ||||||
| 
 | 
 | ||||||
|  | @ -2068,7 +2068,8 @@ static int unix_dgram_recvmsg(struct socket *sock, struct msghdr *msg, | ||||||
| 		if (err != -EAGAIN) | 		if (err != -EAGAIN) | ||||||
| 			break; | 			break; | ||||||
| 	} while (timeo && | 	} while (timeo && | ||||||
| 		 !__skb_wait_for_more_packets(sk, &err, &timeo, last)); | 		 !__skb_wait_for_more_packets(sk, &sk->sk_receive_queue, | ||||||
|  | 					      &err, &timeo, last)); | ||||||
| 
 | 
 | ||||||
| 	if (!skb) { /* implies iolock unlocked */ | 	if (!skb) { /* implies iolock unlocked */ | ||||||
| 		unix_state_lock(sk); | 		unix_state_lock(sk); | ||||||
|  |  | ||||||
		Loading…
	
		Reference in a new issue
	
	 Sabrina Dubroca
						Sabrina Dubroca