]> Pileus Git - ~andy/linux/commitdiff
Merge tag 'rxrpc-20140126' of git://git.kernel.org/pub/scm/linux/kernel/git/dhowells...
authorDavid S. Miller <davem@davemloft.net>
Wed, 29 Jan 2014 02:04:18 +0000 (18:04 -0800)
committerDavid S. Miller <davem@davemloft.net>
Wed, 29 Jan 2014 02:04:18 +0000 (18:04 -0800)
David Howells says:

====================
RxRPC fixes

Here are some small AF_RXRPC fixes.

 (1) Fix a place where a spinlock is taken conditionally but is released
     unconditionally.

 (2) Fix a double-free that happens when cleaning up on a checksum error.

 (3) Fix handling of CHECKSUM_PARTIAL whilst delivering messages to userspace.
====================

Signed-off-by: David S. Miller <davem@davemloft.net>
net/rxrpc/ar-connection.c
net/rxrpc/ar-recvmsg.c

index 4106ca95ec86f43b8c235dd5d94e9fc016ea06f5..7bf5b5b9e8b9400af1cbaecaeaf9a8c222670492 100644 (file)
@@ -381,6 +381,8 @@ static int rxrpc_connect_exclusive(struct rxrpc_sock *rx,
 
                rxrpc_assign_connection_id(conn);
                rx->conn = conn;
+       } else {
+               spin_lock(&trans->client_lock);
        }
 
        /* we've got a connection with a free channel and we can now attach the
index 898492a8d61be8fde5bcdf66084d525bee23b5f0..34b5490dde655ccdbac5dcbbc7b0df1b88ab42ca 100644 (file)
@@ -180,7 +180,8 @@ int rxrpc_recvmsg(struct kiocb *iocb, struct socket *sock,
                if (copy > len - copied)
                        copy = len - copied;
 
-               if (skb->ip_summed == CHECKSUM_UNNECESSARY) {
+               if (skb->ip_summed == CHECKSUM_UNNECESSARY ||
+                   skb->ip_summed == CHECKSUM_PARTIAL) {
                        ret = skb_copy_datagram_iovec(skb, offset,
                                                      msg->msg_iov, copy);
                } else {
@@ -353,6 +354,10 @@ csum_copy_error:
        if (continue_call)
                rxrpc_put_call(continue_call);
        rxrpc_kill_skb(skb);
+       if (!(flags & MSG_PEEK)) {
+               if (skb_dequeue(&rx->sk.sk_receive_queue) != skb)
+                       BUG();
+       }
        skb_kill_datagram(&rx->sk, skb, flags);
        rxrpc_put_call(call);
        return -EAGAIN;