tcp: fix kernel panic with listening_get_next
# BUG: unable to handle kernel NULL pointer dereference at
0000000000000038
IP: [<
ffffffff821ed01e>] listening_get_next+0x50/0x1b3
PGD
11e4b9067 PUD
11d16c067 PMD 0
Oops: 0000 [1] SMP
last sysfs file: /sys/devices/system/cpu/cpu3/cache/index2/shared_cpu_map
CPU 3
Modules linked in: bridge ipv6 button battery ac loop dm_mod tg3 ext3
jbd edd fan thermal processor thermal_sys hwmon sg sata_svw libata dock
serverworks sd_mod scsi_mod ide_disk ide_core [last unloaded: freq_table]
Pid: 3368, comm: slpd Not tainted 2.6.26-rc2-mm1-lxc4 #1
RIP: 0010:[<
ffffffff821ed01e>] [<
ffffffff821ed01e>]
listening_get_next+0x50/0x1b3
RSP: 0018:
ffff81011e1fbe18 EFLAGS:
00010246
RAX:
0000000000000000 RBX:
ffff8100be0ad3c0 RCX:
ffff8100619f50c0
RDX:
ffffffff82475be0 RSI:
ffff81011d9ae6c0 RDI:
ffff8100be0ad508
RBP:
ffff81011f4f1240 R08:
00000000ffffffff R09:
ffff8101185b6780
R10:
000000000000002d R11:
ffffffff820fdbfa R12:
ffff8100be0ad3c8
R13:
ffff8100be0ad6a0 R14:
ffff8100be0ad3c0 R15:
ffffffff825b8ce0
FS:
00007f6a0ebd16d0(0000) GS:
ffff81011f424540(0000)
knlGS:
0000000000000000
CS: 0010 DS: 0000 ES: 0000 CR0:
000000008005003b
CR2:
0000000000000038 CR3:
000000011dc20000 CR4:
00000000000006e0
DR0:
0000000000000000 DR1:
0000000000000000 DR2:
0000000000000000
DR3:
0000000000000000 DR6:
00000000ffff0ff0 DR7:
0000000000000400
Process slpd (pid: 3368, threadinfo
ffff81011e1fa000, task
ffff81011f4b8660)
Stack:
00000000000002ee ffff81011f5a57c0 ffff81011f4f1240
ffff81011e1fbe90
0000000000001000 0000000000000000 00007fff16bf2590 ffffffff821ed9c8
ffff81011f5a57c0 ffff81011d9ae6c0 000000000000041a ffffffff820b0abd
Call Trace:
[<
ffffffff821ed9c8>] ? tcp_seq_next+0x34/0x7e
[<
ffffffff820b0abd>] ? seq_read+0x1aa/0x29d
[<
ffffffff820d21b4>] ? proc_reg_read+0x73/0x8e
[<
ffffffff8209769c>] ? vfs_read+0xaa/0x152
[<
ffffffff82097a7d>] ? sys_read+0x45/0x6e
[<
ffffffff8200bd2b>] ? system_call_after_swapgs+0x7b/0x80
Code: 31 a9 25 00 e9 b5 00 00 00 ff 45 20 83 7d 0c 01 75 79 4c 8b 75 10
48 8b 0e eb 1d 48 8b 51 20 0f b7 45 08 39 02 75 0e 48 8b 41 28 <4c> 39
78 38 0f 84 93 00 00 00 48 8b 09 48 85 c9 75 de 8b 55 1c
RIP [<
ffffffff821ed01e>] listening_get_next+0x50/0x1b3
RSP <
ffff81011e1fbe18>
CR2:
0000000000000038
This kernel panic appears with CONFIG_NET_NS=y.
How to reproduce ?
On the buggy host (host A)
* ip addr add 1.2.3.4/24 dev eth0
On a remote host (host B)
* ip addr add 1.2.3.5/24 dev eth0
* iptables -A INPUT -p tcp -s 1.2.3.4 -j DROP
* ssh 1.2.3.4
On host A:
* netstat -ta or cat /proc/net/tcp
This bug happens when reading /proc/net/tcp[6] when there is a req_sock
at the SYN_RECV state.
When a SYN is received the minisock is created and the sk field is set to
NULL. In the listening_get_next function, we try to look at the field
req->sk->sk_net.
When looking at how to fix this bug, I noticed that is useless to do
the check for the minisock belonging to the namespace. A minisock belongs
to a listen point and this one is per namespace, so when browsing the
minisock they are always per namespace.
Signed-off-by: Daniel Lezcano <dlezcano@fr.ibm.com>
Signed-off-by: David S. Miller <davem@davemloft.net>