On Mon, Jan 9, 2017 at 9:20 AM, Andrey Konovalov <andreyk...@google.com> wrote:
> Hi!
>
> I've got the following error report while running the syzkaller fuzzer.
>
> On commit a121103c922847ba5010819a3f250f1f7fc84ab8 (4.10-rc3).
>
> A reproducer is attached.
>
> ------------[ cut here ]------------
> WARNING: CPU: 0 PID: 4114 at kernel/sched/core.c:7737 
> __might_sleep+0x149/0x1a0
> do not call blocking ops when !TASK_RUNNING; state=1 set at
> [<ffffffff813fcb22>] prepare_to_wait+0x182/0x530
> Modules linked in:
> CPU: 0 PID: 4114 Comm: a.out Not tainted 4.10.0-rc3+ #59
> Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS Bochs 01/01/2011
> Call Trace:
>  __dump_stack lib/dump_stack.c:15
>  dump_stack+0x292/0x398 lib/dump_stack.c:51
>  __warn+0x19f/0x1e0 kernel/panic.c:547
>  warn_slowpath_fmt+0xc5/0x110 kernel/panic.c:562
>  __might_sleep+0x149/0x1a0 kernel/sched/core.c:7732
>  slab_pre_alloc_hook mm/slab.h:408
>  slab_alloc_node mm/slub.c:2634
>  kmem_cache_alloc_node+0x14a/0x280 mm/slub.c:2744
>  __alloc_skb+0x10f/0x800 net/core/skbuff.c:219
>  alloc_skb ./include/linux/skbuff.h:926
>  alloc_tx net/atm/common.c:75
>  vcc_sendmsg+0x5e8/0x1010 net/atm/common.c:609
>  sock_sendmsg_nosec net/socket.c:635
>  sock_sendmsg+0xca/0x110 net/socket.c:645
>  ___sys_sendmsg+0x9d2/0xae0 net/socket.c:1985
>  __sys_sendmsg+0x138/0x320 net/socket.c:2019
>  SYSC_sendmsg net/socket.c:2030
>  SyS_sendmsg+0x2d/0x50 net/socket.c:2026
>  entry_SYSCALL_64_fastpath+0x1f/0xc2 arch/x86/entry/entry_64.S:203
> RIP: 0033:0x7fcbacfddb79
> RSP: 002b:00007ffed8b5a7b8 EFLAGS: 00000206 ORIG_RAX: 000000000000002e
> RAX: ffffffffffffffda RBX: 00007ffed8b5a950 RCX: 00007fcbacfddb79
> RDX: 000000000000c000 RSI: 0000000020002000 RDI: 0000000000000003
> RBP: 0000000000400af0 R08: 0000000000000000 R09: 0000000000000000
> R10: 0000000000000000 R11: 0000000000000206 R12: 0000000000000000
> R13: 00007ffed8b5a950 R14: 0000000000000000 R15: 0000000000000000
> ---[ end trace 9edf2da84d8112da ]---
> atm:sigd_send: bad message type 0

The fix should be straight-forward. Mind to try the attached patch?
diff --git a/net/atm/common.c b/net/atm/common.c
index a3ca922..b7d9661 100644
--- a/net/atm/common.c
+++ b/net/atm/common.c
@@ -571,8 +571,8 @@ int vcc_recvmsg(struct socket *sock, struct msghdr *msg, 
size_t size,
 
 int vcc_sendmsg(struct socket *sock, struct msghdr *m, size_t size)
 {
+       DEFINE_WAIT_FUNC(wait, woken_wake_function);
        struct sock *sk = sock->sk;
-       DEFINE_WAIT(wait);
        struct atm_vcc *vcc;
        struct sk_buff *skb;
        int eff, error;
@@ -604,7 +604,7 @@ int vcc_sendmsg(struct socket *sock, struct msghdr *m, 
size_t size)
        }
 
        eff = (size+3) & ~3; /* align to word boundary */
-       prepare_to_wait(sk_sleep(sk), &wait, TASK_INTERRUPTIBLE);
+       add_wait_queue(sk_sleep(sk), &wait);
        error = 0;
        while (!(skb = alloc_tx(vcc, eff))) {
                if (m->msg_flags & MSG_DONTWAIT) {
@@ -612,6 +612,7 @@ int vcc_sendmsg(struct socket *sock, struct msghdr *m, 
size_t size)
                        break;
                }
                schedule();
+               wait_woken(&wait, TASK_INTERRUPTIBLE, MAX_SCHEDULE_TIMEOUT);
                if (signal_pending(current)) {
                        error = -ERESTARTSYS;
                        break;
@@ -623,9 +624,8 @@ int vcc_sendmsg(struct socket *sock, struct msghdr *m, 
size_t size)
                        send_sig(SIGPIPE, current, 0);
                        break;
                }
-               prepare_to_wait(sk_sleep(sk), &wait, TASK_INTERRUPTIBLE);
        }
-       finish_wait(sk_sleep(sk), &wait);
+       remove_wait_queue(sk_sleep(sk), &wait);
        if (error)
                goto out;
        skb->dev = NULL; /* for paths shared with net_device interfaces */

Reply via email to