stable.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* Patch "af-unix: fix use-after-free with concurrent readers while splicing" has been added to the 4.2-stable tree
@ 2015-12-11 16:49 gregkh
  0 siblings, 0 replies; only message in thread
From: gregkh @ 2015-12-11 16:49 UTC (permalink / raw)
  To: hannes, davem, dvyukov, edumazet, eric.dumazet, gregkh
  Cc: stable, stable-commits


This is a note to let you know that I've just added the patch titled

    af-unix: fix use-after-free with concurrent readers while splicing

to the 4.2-stable tree which can be found at:
    http://www.kernel.org/git/?p=linux/kernel/git/stable/stable-queue.git;a=summary

The filename of the patch is:
     af-unix-fix-use-after-free-with-concurrent-readers-while-splicing.patch
and it can be found in the queue-4.2 subdirectory.

If you, or anyone else, feels it should not be added to the stable tree,
please let <stable@vger.kernel.org> know about it.


>From foo@baz Fri Dec 11 11:38:35 EST 2015
From: Hannes Frederic Sowa <hannes@stressinduktion.org>
Date: Tue, 10 Nov 2015 16:23:15 +0100
Subject: af-unix: fix use-after-free with concurrent readers while splicing

From: Hannes Frederic Sowa <hannes@stressinduktion.org>

[ Upstream commit 73ed5d25dce0354ea381d6dc93005c3085fae03d ]

During splicing an af-unix socket to a pipe we have to drop all
af-unix socket locks. While doing so we allow another reader to enter
unix_stream_read_generic which can read, copy and finally free another
skb. If exactly this skb is just in process of being spliced we get a
use-after-free report by kasan.

First, we must make sure to not have a free while the skb is used during
the splice operation. We simply increment its use counter before unlocking
the reader lock.

Stream sockets have the nice characteristic that we don't care about
zero length writes and they never reach the peer socket's queue. That
said, we can take the UNIXCB.consumed field as the indicator if the
skb was already freed from the socket's receive queue. If the skb was
fully consumed after we locked the reader side again we know it has been
dropped by a second reader. We indicate a short read to user space and
abort the current splice operation.

This bug has been found with syzkaller
(http://github.com/google/syzkaller) by Dmitry Vyukov.

Fixes: 2b514574f7e8 ("net: af_unix: implement splice for stream af_unix sockets")
Reported-by: Dmitry Vyukov <dvyukov@google.com>
Cc: Dmitry Vyukov <dvyukov@google.com>
Cc: Eric Dumazet <eric.dumazet@gmail.com>
Acked-by: Eric Dumazet <edumazet@google.com>
Signed-off-by: Hannes Frederic Sowa <hannes@stressinduktion.org>
Signed-off-by: David S. Miller <davem@davemloft.net>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
---
 net/unix/af_unix.c |   18 ++++++++++++++++++
 1 file changed, 18 insertions(+)

--- a/net/unix/af_unix.c
+++ b/net/unix/af_unix.c
@@ -440,6 +440,7 @@ static void unix_release_sock(struct soc
 		if (state == TCP_LISTEN)
 			unix_release_sock(skb->sk, 1);
 		/* passed fds are erased in the kfree_skb hook	      */
+		UNIXCB(skb).consumed = skb->len;
 		kfree_skb(skb);
 	}
 
@@ -2071,6 +2072,7 @@ static int unix_stream_read_generic(stru
 
 	do {
 		int chunk;
+		bool drop_skb;
 		struct sk_buff *skb, *last;
 
 		unix_state_lock(sk);
@@ -2151,7 +2153,11 @@ unlock:
 		}
 
 		chunk = min_t(unsigned int, unix_skb_len(skb) - skip, size);
+		skb_get(skb);
 		chunk = state->recv_actor(skb, skip, chunk, state);
+		drop_skb = !unix_skb_len(skb);
+		/* skb is only safe to use if !drop_skb */
+		consume_skb(skb);
 		if (chunk < 0) {
 			if (copied == 0)
 				copied = -EFAULT;
@@ -2160,6 +2166,18 @@ unlock:
 		copied += chunk;
 		size -= chunk;
 
+		if (drop_skb) {
+			/* the skb was touched by a concurrent reader;
+			 * we should not expect anything from this skb
+			 * anymore and assume it invalid - we can be
+			 * sure it was dropped from the socket queue
+			 *
+			 * let's report a short read
+			 */
+			err = 0;
+			break;
+		}
+
 		/* Mark read part of skb as used */
 		if (!(flags & MSG_PEEK)) {
 			UNIXCB(skb).consumed += chunk;


Patches currently in stable-queue which might be from hannes@stressinduktion.org are

queue-4.2/ipv6-add-complete-rcu-protection-around-np-opt.patch
queue-4.2/ipv6-check-rt-dst.from-for-the-dst_nocache-route.patch
queue-4.2/af-unix-passcred-support-for-sendpage.patch
queue-4.2/af_unix-don-t-append-consumed-skbs-to-sk_receive_queue.patch
queue-4.2/ipv6-avoid-creating-rtf_cache-from-a-rt-that-is-not-managed-by-fib6-tree.patch
queue-4.2/net-scm-fix-pax-detected-msg_controllen-overflow-in-scm_detach_fds.patch
queue-4.2/ipv6-check-expire-on-dst_nocache-route.patch
queue-4.2/af-unix-fix-use-after-free-with-concurrent-readers-while-splicing.patch
queue-4.2/ip_tunnel-disable-preemption-when-updating-per-cpu-tstats.patch
queue-4.2/af_unix-take-receive-queue-lock-while-appending-new-skb.patch

^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2015-12-11 20:22 UTC | newest]

Thread overview: (only message) (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2015-12-11 16:49 Patch "af-unix: fix use-after-free with concurrent readers while splicing" has been added to the 4.2-stable tree gregkh

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).