linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* Re: net/kcm: WARNING in kcm_write_msgs
       [not found] <CACT4Y+YSSKXzmJQ2J6nMCjD_32rgoqgLYkUjVGz8YswK1Uquvw@mail.gmail.com>
@ 2017-02-06 12:43 ` Dmitry Vyukov
  2017-02-06 23:46   ` Cong Wang
  0 siblings, 1 reply; 2+ messages in thread
From: Dmitry Vyukov @ 2017-02-06 12:43 UTC (permalink / raw)
  To: David Miller, Tom Herbert, Cong Wang, Alexei Starovoitov,
	Al Viro, Daniel Borkmann, netdev, LKML, Eric Dumazet
  Cc: syzkaller

[resending as plain text]

Hello,

The following program triggers WARNING in kcm_write_msgs:

WARNING: CPU: 3 PID: 2936 at net/kcm/kcmsock.c:627
kcm_write_msgs+0x12e3/0x1b90 net/kcm/kcmsock.c:627
CPU: 3 PID: 2936 Comm: a.out Not tainted 4.10.0-rc6+ #209
Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS Bochs 01/01/2011
Call Trace:
 __dump_stack lib/dump_stack.c:15 [inline]
 dump_stack+0x2ee/0x3ef lib/dump_stack.c:51
 panic+0x1fb/0x412 kernel/panic.c:179
 __warn+0x1c4/0x1e0 kernel/panic.c:539
 warn_slowpath_null+0x2c/0x40 kernel/panic.c:582
 kcm_write_msgs+0x12e3/0x1b90 net/kcm/kcmsock.c:627
 kcm_sendmsg+0x163a/0x2200 net/kcm/kcmsock.c:1029
 sock_sendmsg_nosec net/socket.c:635 [inline]
 sock_sendmsg+0xca/0x110 net/socket.c:645
 sock_write_iter+0x326/0x600 net/socket.c:848
 new_sync_write fs/read_write.c:499 [inline]
 __vfs_write+0x483/0x740 fs/read_write.c:512
 vfs_write+0x187/0x530 fs/read_write.c:560
 SYSC_write fs/read_write.c:607 [inline]
 SyS_write+0xfb/0x230 fs/read_write.c:599
 entry_SYSCALL_64_fastpath+0x1f/0xc2
RIP: 0033:0x434c09
RSP: 002b:00007fff40f2d7b8 EFLAGS: 00000217 ORIG_RAX: 0000000000000001
RAX: ffffffffffffffda RBX: 0000000000401960 RCX: 0000000000434c09
RDX: 0000000000000000 RSI: 00000000208aaf27 RDI: 0000000000000005
RBP: 0000000000000000 R08: 0000000000000000 R09: 00007fff00000000
R10: 0000000000000000 R11: 0000000000000217 R12: 00000000004002b0
R13: 0000000000401960 R14: 00000000004019f0 R15: 0000000000000000

// autogenerated by syzkaller (http://github.com/google/syzkaller)
#define _GNU_SOURCE
#include <sys/ioctl.h>
#include <sys/stat.h>
#include <sys/syscall.h>
#include <sys/time.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <linux/in.h>
#include <stddef.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>

#ifndef __NR_bpf
#define __NR_bpf 321
#endif
#ifndef AF_KCM
#define AF_KCM 0x29
#endif

int main()
{
  syscall(__NR_mmap, 0x20000000ul, 0xfff000ul, 0x3ul, 0x32ul, -1, 0);
  int sock = socket(AF_INET6, SOCK_STREAM, IPPROTO_IP);
  (*(uint32_t*)0x20b4ffd0 = (uint32_t)0x1);
  (*(uint32_t*)0x20b4ffd4 = (uint32_t)0x2);
  (*(uint64_t*)0x20b4ffd8 = (uint64_t)0x20b4f000);
  (*(uint64_t*)0x20b4ffe0 = (uint64_t)0x2015a000);
  (*(uint32_t*)0x20b4ffe8 = (uint32_t)0x9);
  (*(uint32_t*)0x20b4ffec = (uint32_t)0x80);
  (*(uint64_t*)0x20b4fff0 = (uint64_t)0x20b4f000);
  (*(uint32_t*)0x20b4fff8 = (uint32_t)0x0);
  (*(uint8_t*)0x20b4f000 = (uint8_t)0xffffffffffffffb7);
  (*(uint8_t*)0x20b4f001 = (uint8_t)0x0);
  (*(uint16_t*)0x20b4f002 = (uint16_t)0x0);
  (*(uint32_t*)0x20b4f004 = (uint32_t)0x0);
  (*(uint8_t*)0x20b4f008 = (uint8_t)0x9595);
  (*(uint8_t*)0x20b4f009 = (uint8_t)0x0);
  (*(uint16_t*)0x20b4f00a = (uint16_t)0x0);
  (*(uint32_t*)0x20b4f00c = (uint32_t)0x0);
  (memcpy((void*)0x2015a000, "\x00\x8b", 2));
  int bpf = syscall(__NR_bpf, 0x5ul, 0x20b4ffd0ul, 0x30ul, 0, 0,
                          0, 0, 0, 0);
  int sock2 = syscall(__NR_socket, AF_KCM, 0x5ul, 0x0ul);
  (*(uint32_t*)0x20b5c000 = sock);
  (*(uint32_t*)0x20b5c004 = bpf);
  syscall(__NR_ioctl, sock2, 0x89e0ul, 0x20b5c000ul);
  syscall(__NR_write, sock2, 0x208aaf27ul, 0x0ul);
  return 0;
}


On commit a572a1b999489efb591287632279c6c9eca3e4ed

^ permalink raw reply	[flat|nested] 2+ messages in thread

* Re: net/kcm: WARNING in kcm_write_msgs
  2017-02-06 12:43 ` net/kcm: WARNING in kcm_write_msgs Dmitry Vyukov
@ 2017-02-06 23:46   ` Cong Wang
  0 siblings, 0 replies; 2+ messages in thread
From: Cong Wang @ 2017-02-06 23:46 UTC (permalink / raw)
  To: Dmitry Vyukov
  Cc: David Miller, Tom Herbert, Alexei Starovoitov, Al Viro,
	Daniel Borkmann, netdev, LKML, Eric Dumazet, syzkaller

[-- Attachment #1: Type: text/plain, Size: 1406 bytes --]

On Mon, Feb 6, 2017 at 4:43 AM, Dmitry Vyukov <dvyukov@google.com> wrote:
> [resending as plain text]
>
> Hello,
>
> The following program triggers WARNING in kcm_write_msgs:
>
> WARNING: CPU: 3 PID: 2936 at net/kcm/kcmsock.c:627
> kcm_write_msgs+0x12e3/0x1b90 net/kcm/kcmsock.c:627
> CPU: 3 PID: 2936 Comm: a.out Not tainted 4.10.0-rc6+ #209
> Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS Bochs 01/01/2011
> Call Trace:
>  __dump_stack lib/dump_stack.c:15 [inline]
>  dump_stack+0x2ee/0x3ef lib/dump_stack.c:51
>  panic+0x1fb/0x412 kernel/panic.c:179
>  __warn+0x1c4/0x1e0 kernel/panic.c:539
>  warn_slowpath_null+0x2c/0x40 kernel/panic.c:582
>  kcm_write_msgs+0x12e3/0x1b90 net/kcm/kcmsock.c:627
>  kcm_sendmsg+0x163a/0x2200 net/kcm/kcmsock.c:1029
>  sock_sendmsg_nosec net/socket.c:635 [inline]
>  sock_sendmsg+0xca/0x110 net/socket.c:645
>  sock_write_iter+0x326/0x600 net/socket.c:848
>  new_sync_write fs/read_write.c:499 [inline]
>  __vfs_write+0x483/0x740 fs/read_write.c:512
>  vfs_write+0x187/0x530 fs/read_write.c:560
>  SYSC_write fs/read_write.c:607 [inline]
>  SyS_write+0xfb/0x230 fs/read_write.c:599
>  entry_SYSCALL_64_fastpath+0x1f/0xc2
[...]
>   syscall(__NR_write, sock2, 0x208aaf27ul, 0x0ul);

Looks like len == 0 case is not handled correctly in kcm_sendmsg().
The attached patch fixes it, but I am not sure if it is correct in all
cases yet, the logic is complicated.

[-- Attachment #2: kcm.diff --]
[-- Type: text/plain, Size: 1730 bytes --]

diff --git a/net/kcm/kcmsock.c b/net/kcm/kcmsock.c
index 7e08a4d..64f0e85 100644
--- a/net/kcm/kcmsock.c
+++ b/net/kcm/kcmsock.c
@@ -929,23 +929,25 @@ static int kcm_sendmsg(struct socket *sock, struct msghdr *msg, size_t len)
 			goto out_error;
 	}
 
-	/* New message, alloc head skb */
-	head = alloc_skb(0, sk->sk_allocation);
-	while (!head) {
-		kcm_push(kcm);
-		err = sk_stream_wait_memory(sk, &timeo);
-		if (err)
-			goto out_error;
-
+	if (msg_data_left(msg)) {
+		/* New message, alloc head skb */
 		head = alloc_skb(0, sk->sk_allocation);
-	}
+		while (!head) {
+			kcm_push(kcm);
+			err = sk_stream_wait_memory(sk, &timeo);
+			if (err)
+				goto out_error;
 
-	skb = head;
+			head = alloc_skb(0, sk->sk_allocation);
+		}
 
-	/* Set ip_summed to CHECKSUM_UNNECESSARY to avoid calling
-	 * csum_and_copy_from_iter from skb_do_copy_data_nocache.
-	 */
-	skb->ip_summed = CHECKSUM_UNNECESSARY;
+		skb = head;
+
+		/* Set ip_summed to CHECKSUM_UNNECESSARY to avoid calling
+		 * csum_and_copy_from_iter from skb_do_copy_data_nocache.
+		 */
+		skb->ip_summed = CHECKSUM_UNNECESSARY;
+	}
 
 start:
 	while (msg_data_left(msg)) {
@@ -1018,10 +1020,12 @@ static int kcm_sendmsg(struct socket *sock, struct msghdr *msg, size_t len)
 	if (eor) {
 		bool not_busy = skb_queue_empty(&sk->sk_write_queue);
 
-		/* Message complete, queue it on send buffer */
-		__skb_queue_tail(&sk->sk_write_queue, head);
-		kcm->seq_skb = NULL;
-		KCM_STATS_INCR(kcm->stats.tx_msgs);
+		if (head) {
+			/* Message complete, queue it on send buffer */
+			__skb_queue_tail(&sk->sk_write_queue, head);
+			kcm->seq_skb = NULL;
+			KCM_STATS_INCR(kcm->stats.tx_msgs);
+		}
 
 		if (msg->msg_flags & MSG_BATCH) {
 			kcm->tx_wait_more = true;

^ permalink raw reply related	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2017-02-06 23:46 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
     [not found] <CACT4Y+YSSKXzmJQ2J6nMCjD_32rgoqgLYkUjVGz8YswK1Uquvw@mail.gmail.com>
2017-02-06 12:43 ` net/kcm: WARNING in kcm_write_msgs Dmitry Vyukov
2017-02-06 23:46   ` Cong Wang

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).