From 0f831b3cf21d3a7902fa967776d6784eaf8c54cb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fabian=20Gr=C3=BCnbichler?= Date: Thu, 8 Jun 2017 14:17:55 +0200 Subject: [PATCH] add CVE fixes CVE-2017-8890: dccp/tcp: do not inherit mc_list from parent CVE-2017-9074: ipv6: Prevent overrun when parsing v6 header options CVE-2017-9075: sctp: do not inherit ipv6_{mc|ac|fl}_list from parent CVE-2017-9076/CVE-2017-9077: ipv6/dccp: do not inherit ipv6_mc_list from parent CVE-2017-9242: ipv6: fix out of bound writes in __ip6_append_data() --- ...p-do-not-inherit-mc_list-from-parent.patch | 54 ++++ ...errun-when-parsing-v6-header-options.patch | 244 ++++++++++++++++++ ...rit-ipv6_-mc-ac-fl-_list-from-parent.patch | 46 ++++ ...not-inherit-ipv6_mc_list-from-parent.patch | 78 ++++++ ...of-bound-writes-in-__ip6_append_data.patch | 79 ++++++ Makefile | 5 + 6 files changed, 506 insertions(+) create mode 100644 CVE-2017-8890-dccp-tcp-do-not-inherit-mc_list-from-parent.patch create mode 100644 CVE-2017-9074-ipv6-Prevent-overrun-when-parsing-v6-header-options.patch create mode 100644 CVE-2017-9075-sctp-do-not-inherit-ipv6_-mc-ac-fl-_list-from-parent.patch create mode 100644 CVE-2017-9076_9077-ipv6-dccp-do-not-inherit-ipv6_mc_list-from-parent.patch create mode 100644 CVE-2017-9242-ipv6-fix-out-of-bound-writes-in-__ip6_append_data.patch diff --git a/CVE-2017-8890-dccp-tcp-do-not-inherit-mc_list-from-parent.patch b/CVE-2017-8890-dccp-tcp-do-not-inherit-mc_list-from-parent.patch new file mode 100644 index 0000000..3f5d674 --- /dev/null +++ b/CVE-2017-8890-dccp-tcp-do-not-inherit-mc_list-from-parent.patch @@ -0,0 +1,54 @@ +From fa0ad0349d68f7e86419922266aa48de3eb2c507 Mon Sep 17 00:00:00 2001 +From: Eric Dumazet +Date: Tue, 6 Jun 2017 18:16:00 +0200 +Subject: [PATCH] dccp/tcp: do not inherit mc_list from parent +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +syzkaller found a way to trigger double frees from ip_mc_drop_socket() + +It turns out that leave a copy of parent mc_list at accept() time, +which is very bad. + +Very similar to commit 8b485ce69876 ("tcp: do not inherit +fastopen_req from parent") + +Initial report from Pray3r, completed by Andrey one. +Thanks a lot to them ! + +Signed-off-by: Eric Dumazet +Reported-by: Pray3r +Reported-by: Andrey Konovalov +Tested-by: Andrey Konovalov +Signed-off-by: David S. Miller + +CVE-2017-8890 + +(cherry-picked from 657831ffc38e30092a2d5f03d385d710eb88b09a) +Signed-off-by: Stefan Bader +Acked-by: Colin Ian King +Acked-by: Andy Whitcroft +Signed-off-by: Thadeu Lima de Souza Cascardo + +Signed-off-by: Fabian Grünbichler +--- + net/ipv4/inet_connection_sock.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/net/ipv4/inet_connection_sock.c b/net/ipv4/inet_connection_sock.c +index 19ea045c50ed..d952cfa15737 100644 +--- a/net/ipv4/inet_connection_sock.c ++++ b/net/ipv4/inet_connection_sock.c +@@ -669,6 +669,8 @@ struct sock *inet_csk_clone_lock(const struct sock *sk, + /* listeners have SOCK_RCU_FREE, not the children */ + sock_reset_flag(newsk, SOCK_RCU_FREE); + ++ inet_sk(newsk)->mc_list = NULL; ++ + newsk->sk_mark = inet_rsk(req)->ir_mark; + atomic64_set(&newsk->sk_cookie, + atomic64_read(&inet_rsk(req)->ir_cookie)); +-- +2.11.0 + diff --git a/CVE-2017-9074-ipv6-Prevent-overrun-when-parsing-v6-header-options.patch b/CVE-2017-9074-ipv6-Prevent-overrun-when-parsing-v6-header-options.patch new file mode 100644 index 0000000..dfacb10 --- /dev/null +++ b/CVE-2017-9074-ipv6-Prevent-overrun-when-parsing-v6-header-options.patch @@ -0,0 +1,244 @@ +From 1b56ac5ee17e975a07740b4c865918984ec14b52 Mon Sep 17 00:00:00 2001 +From: Craig Gallek +Date: Tue, 16 May 2017 14:36:23 -0400 +Subject: [PATCH] ipv6: Prevent overrun when parsing v6 header options +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +The KASAN warning repoted below was discovered with a syzkaller +program. The reproducer is basically: + int s = socket(AF_INET6, SOCK_RAW, NEXTHDR_HOP); + send(s, &one_byte_of_data, 1, MSG_MORE); + send(s, &more_than_mtu_bytes_data, 2000, 0); + +The socket() call sets the nexthdr field of the v6 header to +NEXTHDR_HOP, the first send call primes the payload with a non zero +byte of data, and the second send call triggers the fragmentation path. + +The fragmentation code tries to parse the header options in order +to figure out where to insert the fragment option. Since nexthdr points +to an invalid option, the calculation of the size of the network header +can made to be much larger than the linear section of the skb and data +is read outside of it. + +This fix makes ip6_find_1stfrag return an error if it detects +running out-of-bounds. + +[ 42.361487] ================================================================== +[ 42.364412] BUG: KASAN: slab-out-of-bounds in ip6_fragment+0x11c8/0x3730 +[ 42.365471] Read of size 840 at addr ffff88000969e798 by task ip6_fragment-oo/3789 +[ 42.366469] +[ 42.366696] CPU: 1 PID: 3789 Comm: ip6_fragment-oo Not tainted 4.11.0+ #41 +[ 42.367628] Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS 1.10.1-1ubuntu1 04/01/2014 +[ 42.368824] Call Trace: +[ 42.369183] dump_stack+0xb3/0x10b +[ 42.369664] print_address_description+0x73/0x290 +[ 42.370325] kasan_report+0x252/0x370 +[ 42.370839] ? ip6_fragment+0x11c8/0x3730 +[ 42.371396] check_memory_region+0x13c/0x1a0 +[ 42.371978] memcpy+0x23/0x50 +[ 42.372395] ip6_fragment+0x11c8/0x3730 +[ 42.372920] ? nf_ct_expect_unregister_notifier+0x110/0x110 +[ 42.373681] ? ip6_copy_metadata+0x7f0/0x7f0 +[ 42.374263] ? ip6_forward+0x2e30/0x2e30 +[ 42.374803] ip6_finish_output+0x584/0x990 +[ 42.375350] ip6_output+0x1b7/0x690 +[ 42.375836] ? ip6_finish_output+0x990/0x990 +[ 42.376411] ? ip6_fragment+0x3730/0x3730 +[ 42.376968] ip6_local_out+0x95/0x160 +[ 42.377471] ip6_send_skb+0xa1/0x330 +[ 42.377969] ip6_push_pending_frames+0xb3/0xe0 +[ 42.378589] rawv6_sendmsg+0x2051/0x2db0 +[ 42.379129] ? rawv6_bind+0x8b0/0x8b0 +[ 42.379633] ? _copy_from_user+0x84/0xe0 +[ 42.380193] ? debug_check_no_locks_freed+0x290/0x290 +[ 42.380878] ? ___sys_sendmsg+0x162/0x930 +[ 42.381427] ? rcu_read_lock_sched_held+0xa3/0x120 +[ 42.382074] ? sock_has_perm+0x1f6/0x290 +[ 42.382614] ? ___sys_sendmsg+0x167/0x930 +[ 42.383173] ? lock_downgrade+0x660/0x660 +[ 42.383727] inet_sendmsg+0x123/0x500 +[ 42.384226] ? inet_sendmsg+0x123/0x500 +[ 42.384748] ? inet_recvmsg+0x540/0x540 +[ 42.385263] sock_sendmsg+0xca/0x110 +[ 42.385758] SYSC_sendto+0x217/0x380 +[ 42.386249] ? SYSC_connect+0x310/0x310 +[ 42.386783] ? __might_fault+0x110/0x1d0 +[ 42.387324] ? lock_downgrade+0x660/0x660 +[ 42.387880] ? __fget_light+0xa1/0x1f0 +[ 42.388403] ? __fdget+0x18/0x20 +[ 42.388851] ? sock_common_setsockopt+0x95/0xd0 +[ 42.389472] ? SyS_setsockopt+0x17f/0x260 +[ 42.390021] ? entry_SYSCALL_64_fastpath+0x5/0xbe +[ 42.390650] SyS_sendto+0x40/0x50 +[ 42.391103] entry_SYSCALL_64_fastpath+0x1f/0xbe +[ 42.391731] RIP: 0033:0x7fbbb711e383 +[ 42.392217] RSP: 002b:00007ffff4d34f28 EFLAGS: 00000246 ORIG_RAX: 000000000000002c +[ 42.393235] RAX: ffffffffffffffda RBX: 0000000000000000 RCX: 00007fbbb711e383 +[ 42.394195] RDX: 0000000000001000 RSI: 00007ffff4d34f60 RDI: 0000000000000003 +[ 42.395145] RBP: 0000000000000046 R08: 00007ffff4d34f40 R09: 0000000000000018 +[ 42.396056] R10: 0000000000000000 R11: 0000000000000246 R12: 0000000000400aad +[ 42.396598] R13: 0000000000000066 R14: 00007ffff4d34ee0 R15: 00007fbbb717af00 +[ 42.397257] +[ 42.397411] Allocated by task 3789: +[ 42.397702] save_stack_trace+0x16/0x20 +[ 42.398005] save_stack+0x46/0xd0 +[ 42.398267] kasan_kmalloc+0xad/0xe0 +[ 42.398548] kasan_slab_alloc+0x12/0x20 +[ 42.398848] __kmalloc_node_track_caller+0xcb/0x380 +[ 42.399224] __kmalloc_reserve.isra.32+0x41/0xe0 +[ 42.399654] __alloc_skb+0xf8/0x580 +[ 42.400003] sock_wmalloc+0xab/0xf0 +[ 42.400346] __ip6_append_data.isra.41+0x2472/0x33d0 +[ 42.400813] ip6_append_data+0x1a8/0x2f0 +[ 42.401122] rawv6_sendmsg+0x11ee/0x2db0 +[ 42.401505] inet_sendmsg+0x123/0x500 +[ 42.401860] sock_sendmsg+0xca/0x110 +[ 42.402209] ___sys_sendmsg+0x7cb/0x930 +[ 42.402582] __sys_sendmsg+0xd9/0x190 +[ 42.402941] SyS_sendmsg+0x2d/0x50 +[ 42.403273] entry_SYSCALL_64_fastpath+0x1f/0xbe +[ 42.403718] +[ 42.403871] Freed by task 1794: +[ 42.404146] save_stack_trace+0x16/0x20 +[ 42.404515] save_stack+0x46/0xd0 +[ 42.404827] kasan_slab_free+0x72/0xc0 +[ 42.405167] kfree+0xe8/0x2b0 +[ 42.405462] skb_free_head+0x74/0xb0 +[ 42.405806] skb_release_data+0x30e/0x3a0 +[ 42.406198] skb_release_all+0x4a/0x60 +[ 42.406563] consume_skb+0x113/0x2e0 +[ 42.406910] skb_free_datagram+0x1a/0xe0 +[ 42.407288] netlink_recvmsg+0x60d/0xe40 +[ 42.407667] sock_recvmsg+0xd7/0x110 +[ 42.408022] ___sys_recvmsg+0x25c/0x580 +[ 42.408395] __sys_recvmsg+0xd6/0x190 +[ 42.408753] SyS_recvmsg+0x2d/0x50 +[ 42.409086] entry_SYSCALL_64_fastpath+0x1f/0xbe +[ 42.409513] +[ 42.409665] The buggy address belongs to the object at ffff88000969e780 +[ 42.409665] which belongs to the cache kmalloc-512 of size 512 +[ 42.410846] The buggy address is located 24 bytes inside of +[ 42.410846] 512-byte region [ffff88000969e780, ffff88000969e980) +[ 42.411941] The buggy address belongs to the page: +[ 42.412405] page:ffffea000025a780 count:1 mapcount:0 mapping: (null) index:0x0 compound_mapcount: 0 +[ 42.413298] flags: 0x100000000008100(slab|head) +[ 42.413729] raw: 0100000000008100 0000000000000000 0000000000000000 00000001800c000c +[ 42.414387] raw: ffffea00002a9500 0000000900000007 ffff88000c401280 0000000000000000 +[ 42.415074] page dumped because: kasan: bad access detected +[ 42.415604] +[ 42.415757] Memory state around the buggy address: +[ 42.416222] ffff88000969e880: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 +[ 42.416904] ffff88000969e900: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 +[ 42.417591] >ffff88000969e980: fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc fc +[ 42.418273] ^ +[ 42.418588] ffff88000969ea00: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb +[ 42.419273] ffff88000969ea80: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb +[ 42.419882] ================================================================== + +Reported-by: Andrey Konovalov +Signed-off-by: Craig Gallek +Signed-off-by: David S. Miller + +CVE-2017-9074 + +(cherry-picked from 2423496af35d94a87156b063ea5cedffc10a70a1) +Signed-off-by: Stefan Bader +Acked-by: Colin King +Acked-by: Andy Whitcroft +Signed-off-by: Thadeu Lima de Souza Cascardo + +Signed-off-by: Fabian Grünbichler +--- + net/ipv6/ip6_offload.c | 2 ++ + net/ipv6/ip6_output.c | 4 ++++ + net/ipv6/output_core.c | 14 ++++++++------ + net/ipv6/udp_offload.c | 2 ++ + 4 files changed, 16 insertions(+), 6 deletions(-) + +diff --git a/net/ipv6/ip6_offload.c b/net/ipv6/ip6_offload.c +index 33b04ec2744a..9881a87696bc 100644 +--- a/net/ipv6/ip6_offload.c ++++ b/net/ipv6/ip6_offload.c +@@ -117,6 +117,8 @@ static struct sk_buff *ipv6_gso_segment(struct sk_buff *skb, + + if (udpfrag) { + unfrag_ip6hlen = ip6_find_1stfragopt(skb, &prevhdr); ++ if (unfrag_ip6hlen < 0) ++ return ERR_PTR(unfrag_ip6hlen); + fptr = (struct frag_hdr *)((u8 *)ipv6h + unfrag_ip6hlen); + fptr->frag_off = htons(offset); + if (skb->next) +diff --git a/net/ipv6/ip6_output.c b/net/ipv6/ip6_output.c +index d57f4ee5ec29..8f0814d301aa 100644 +--- a/net/ipv6/ip6_output.c ++++ b/net/ipv6/ip6_output.c +@@ -597,6 +597,10 @@ int ip6_fragment(struct net *net, struct sock *sk, struct sk_buff *skb, + u8 *prevhdr, nexthdr = 0; + + hlen = ip6_find_1stfragopt(skb, &prevhdr); ++ if (hlen < 0) { ++ err = hlen; ++ goto fail; ++ } + nexthdr = *prevhdr; + + mtu = ip6_skb_dst_mtu(skb); +diff --git a/net/ipv6/output_core.c b/net/ipv6/output_core.c +index cd4252346a32..e9065b8d3af8 100644 +--- a/net/ipv6/output_core.c ++++ b/net/ipv6/output_core.c +@@ -79,14 +79,13 @@ EXPORT_SYMBOL(ipv6_select_ident); + int ip6_find_1stfragopt(struct sk_buff *skb, u8 **nexthdr) + { + u16 offset = sizeof(struct ipv6hdr); +- struct ipv6_opt_hdr *exthdr = +- (struct ipv6_opt_hdr *)(ipv6_hdr(skb) + 1); + unsigned int packet_len = skb_tail_pointer(skb) - + skb_network_header(skb); + int found_rhdr = 0; + *nexthdr = &ipv6_hdr(skb)->nexthdr; + +- while (offset + 1 <= packet_len) { ++ while (offset <= packet_len) { ++ struct ipv6_opt_hdr *exthdr; + + switch (**nexthdr) { + +@@ -107,13 +106,16 @@ int ip6_find_1stfragopt(struct sk_buff *skb, u8 **nexthdr) + return offset; + } + +- offset += ipv6_optlen(exthdr); +- *nexthdr = &exthdr->nexthdr; ++ if (offset + sizeof(struct ipv6_opt_hdr) > packet_len) ++ return -EINVAL; ++ + exthdr = (struct ipv6_opt_hdr *)(skb_network_header(skb) + + offset); ++ offset += ipv6_optlen(exthdr); ++ *nexthdr = &exthdr->nexthdr; + } + +- return offset; ++ return -EINVAL; + } + EXPORT_SYMBOL(ip6_find_1stfragopt); + +diff --git a/net/ipv6/udp_offload.c b/net/ipv6/udp_offload.c +index ac858c480f2f..b348cff47395 100644 +--- a/net/ipv6/udp_offload.c ++++ b/net/ipv6/udp_offload.c +@@ -91,6 +91,8 @@ static struct sk_buff *udp6_ufo_fragment(struct sk_buff *skb, + * bytes to insert fragment header. + */ + unfrag_ip6hlen = ip6_find_1stfragopt(skb, &prevhdr); ++ if (unfrag_ip6hlen < 0) ++ return ERR_PTR(unfrag_ip6hlen); + nexthdr = *prevhdr; + *prevhdr = NEXTHDR_FRAGMENT; + unfrag_len = (skb_network_header(skb) - skb_mac_header(skb)) + +-- +2.11.0 + diff --git a/CVE-2017-9075-sctp-do-not-inherit-ipv6_-mc-ac-fl-_list-from-parent.patch b/CVE-2017-9075-sctp-do-not-inherit-ipv6_-mc-ac-fl-_list-from-parent.patch new file mode 100644 index 0000000..0849a06 --- /dev/null +++ b/CVE-2017-9075-sctp-do-not-inherit-ipv6_-mc-ac-fl-_list-from-parent.patch @@ -0,0 +1,46 @@ +From eaa390df0e82e771601fa68482c4f022674e904f Mon Sep 17 00:00:00 2001 +From: Eric Dumazet +Date: Wed, 17 May 2017 07:16:40 -0700 +Subject: [PATCH] sctp: do not inherit ipv6_{mc|ac|fl}_list from parent +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +SCTP needs fixes similar to 83eaddab4378 ("ipv6/dccp: do not inherit +ipv6_mc_list from parent"), otherwise bad things can happen. + +Signed-off-by: Eric Dumazet +Reported-by: Andrey Konovalov +Tested-by: Andrey Konovalov +Signed-off-by: David S. Miller + +CVE-2017-9075 + +(cherry-picked from fdcee2cbb8438702ea1b328fb6e0ac5e9a40c7f8) +Signed-off-by: Stefan Bader +Acked-by: Colin King +Acked-by: Andy Whitcroft +Signed-off-by: Thadeu Lima de Souza Cascardo + +Signed-off-by: Fabian Grünbichler +--- + net/sctp/ipv6.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/net/sctp/ipv6.c b/net/sctp/ipv6.c +index 64dfd35ccdcc..ef0ed6bb71e9 100644 +--- a/net/sctp/ipv6.c ++++ b/net/sctp/ipv6.c +@@ -666,6 +666,9 @@ static struct sock *sctp_v6_create_accept_sk(struct sock *sk, + newnp = inet6_sk(newsk); + + memcpy(newnp, np, sizeof(struct ipv6_pinfo)); ++ newnp->ipv6_mc_list = NULL; ++ newnp->ipv6_ac_list = NULL; ++ newnp->ipv6_fl_list = NULL; + + rcu_read_lock(); + opt = rcu_dereference(np->opt); +-- +2.11.0 + diff --git a/CVE-2017-9076_9077-ipv6-dccp-do-not-inherit-ipv6_mc_list-from-parent.patch b/CVE-2017-9076_9077-ipv6-dccp-do-not-inherit-ipv6_mc_list-from-parent.patch new file mode 100644 index 0000000..d523e96 --- /dev/null +++ b/CVE-2017-9076_9077-ipv6-dccp-do-not-inherit-ipv6_mc_list-from-parent.patch @@ -0,0 +1,78 @@ +From ef8ae9e80ab0846763c6405968852e19c9a87782 Mon Sep 17 00:00:00 2001 +From: WANG Cong +Date: Wed, 7 Jun 2017 12:28:27 +0200 +Subject: [PATCH] ipv6/dccp: do not inherit ipv6_mc_list from parent +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +Like commit 657831ffc38e ("dccp/tcp: do not inherit mc_list from parent") +we should clear ipv6_mc_list etc. for IPv6 sockets too. + +Cc: Eric Dumazet +Signed-off-by: Cong Wang +Acked-by: Eric Dumazet +Signed-off-by: David S. Miller + +CVE-2017-9076 +CVE-2017-9077 + +(cherry-picked from 83eaddab4378db256d00d295bda6ca997cd13a52) +Signed-off-by: Stefan Bader +Acked-by: Colin Ian King +Acked-by: Andy Whitcroft +Signed-off-by: Thadeu Lima de Souza Cascardo + +Signed-off-by: Fabian Grünbichler +--- + net/dccp/ipv6.c | 6 ++++++ + net/ipv6/tcp_ipv6.c | 2 ++ + 2 files changed, 8 insertions(+) + +diff --git a/net/dccp/ipv6.c b/net/dccp/ipv6.c +index 2f3e8bbe2cb9..8f41327c1edf 100644 +--- a/net/dccp/ipv6.c ++++ b/net/dccp/ipv6.c +@@ -426,6 +426,9 @@ static struct sock *dccp_v6_request_recv_sock(const struct sock *sk, + newsk->sk_backlog_rcv = dccp_v4_do_rcv; + newnp->pktoptions = NULL; + newnp->opt = NULL; ++ newnp->ipv6_mc_list = NULL; ++ newnp->ipv6_ac_list = NULL; ++ newnp->ipv6_fl_list = NULL; + newnp->mcast_oif = inet6_iif(skb); + newnp->mcast_hops = ipv6_hdr(skb)->hop_limit; + +@@ -490,6 +493,9 @@ static struct sock *dccp_v6_request_recv_sock(const struct sock *sk, + /* Clone RX bits */ + newnp->rxopt.all = np->rxopt.all; + ++ newnp->ipv6_mc_list = NULL; ++ newnp->ipv6_ac_list = NULL; ++ newnp->ipv6_fl_list = NULL; + newnp->pktoptions = NULL; + newnp->opt = NULL; + newnp->mcast_oif = inet6_iif(skb); +diff --git a/net/ipv6/tcp_ipv6.c b/net/ipv6/tcp_ipv6.c +index cfc232714139..c0ca1218801b 100644 +--- a/net/ipv6/tcp_ipv6.c ++++ b/net/ipv6/tcp_ipv6.c +@@ -1055,6 +1055,7 @@ static struct sock *tcp_v6_syn_recv_sock(const struct sock *sk, struct sk_buff * + newtp->af_specific = &tcp_sock_ipv6_mapped_specific; + #endif + ++ newnp->ipv6_mc_list = NULL; + newnp->ipv6_ac_list = NULL; + newnp->ipv6_fl_list = NULL; + newnp->pktoptions = NULL; +@@ -1124,6 +1125,7 @@ static struct sock *tcp_v6_syn_recv_sock(const struct sock *sk, struct sk_buff * + First: no IPv4 options. + */ + newinet->inet_opt = NULL; ++ newnp->ipv6_mc_list = NULL; + newnp->ipv6_ac_list = NULL; + newnp->ipv6_fl_list = NULL; + +-- +2.11.0 + diff --git a/CVE-2017-9242-ipv6-fix-out-of-bound-writes-in-__ip6_append_data.patch b/CVE-2017-9242-ipv6-fix-out-of-bound-writes-in-__ip6_append_data.patch new file mode 100644 index 0000000..3f08164 --- /dev/null +++ b/CVE-2017-9242-ipv6-fix-out-of-bound-writes-in-__ip6_append_data.patch @@ -0,0 +1,79 @@ +From 2bb2c56a2089211713a7b1fb379cce741f65ea9e Mon Sep 17 00:00:00 2001 +From: Eric Dumazet +Date: Fri, 19 May 2017 14:17:48 -0700 +Subject: [PATCH] ipv6: fix out of bound writes in __ip6_append_data() +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +Andrey Konovalov and idaifish@gmail.com reported crashes caused by +one skb shared_info being overwritten from __ip6_append_data() + +Andrey program lead to following state : + +copy -4200 datalen 2000 fraglen 2040 +maxfraglen 2040 alloclen 2048 transhdrlen 0 offset 0 fraggap 6200 + +The skb_copy_and_csum_bits(skb_prev, maxfraglen, data + transhdrlen, +fraggap, 0); is overwriting skb->head and skb_shared_info + +Since we apparently detect this rare condition too late, move the +code earlier to even avoid allocating skb and risking crashes. + +Once again, many thanks to Andrey and syzkaller team. + +Signed-off-by: Eric Dumazet +Reported-by: Andrey Konovalov +Tested-by: Andrey Konovalov +Reported-by: +Signed-off-by: David S. Miller + +CVE-2017-9242 + +(cherry-picked from 232cd35d0804cc241eb887bb8d4d9b3b9881c64a) +Signed-off-by: Stefan Bader +Acked-by: Colin King +Acked-by: Andy Whitcroft +Signed-off-by: Thadeu Lima de Souza Cascardo + +Signed-off-by: Fabian Grünbichler +--- + net/ipv6/ip6_output.c | 15 ++++++++------- + 1 file changed, 8 insertions(+), 7 deletions(-) + +diff --git a/net/ipv6/ip6_output.c b/net/ipv6/ip6_output.c +index 8f0814d301aa..135ee573eaef 100644 +--- a/net/ipv6/ip6_output.c ++++ b/net/ipv6/ip6_output.c +@@ -1463,6 +1463,11 @@ static int __ip6_append_data(struct sock *sk, + */ + alloclen += sizeof(struct frag_hdr); + ++ copy = datalen - transhdrlen - fraggap; ++ if (copy < 0) { ++ err = -EINVAL; ++ goto error; ++ } + if (transhdrlen) { + skb = sock_alloc_send_skb(sk, + alloclen + hh_len, +@@ -1512,13 +1517,9 @@ static int __ip6_append_data(struct sock *sk, + data += fraggap; + pskb_trim_unique(skb_prev, maxfraglen); + } +- copy = datalen - transhdrlen - fraggap; +- +- if (copy < 0) { +- err = -EINVAL; +- kfree_skb(skb); +- goto error; +- } else if (copy > 0 && getfrag(from, data + transhdrlen, offset, copy, fraggap, skb) < 0) { ++ if (copy > 0 && ++ getfrag(from, data + transhdrlen, offset, ++ copy, fraggap, skb) < 0) { + err = -EFAULT; + kfree_skb(skb); + goto error; +-- +2.11.0 + diff --git a/Makefile b/Makefile index 0e37389..982ded9 100644 --- a/Makefile +++ b/Makefile @@ -235,6 +235,11 @@ ${KERNEL_SRC}/README ${KERNEL_CFG_ORG}: ${KERNEL_SRC_SUBMODULE} | submodules cd ${KERNEL_SRC}; patch -p1 < ../cgroup-cpuset-add-cpuset.remap_cpus.patch cd ${KERNEL_SRC}; patch -p1 < ../openvswitch-Set-internal-device-max-mtu-to-ETH_MAX_M.patch cd ${KERNEL_SRC}; patch -p1 < ../0001-netfilter-nft_set_rbtree-handle-re-addition-element-.patch # DoS from within (unpriv) containers + cd ${KERNEL_SRC}; patch -p1 < ../CVE-2017-8890-dccp-tcp-do-not-inherit-mc_list-from-parent.patch + cd ${KERNEL_SRC}; patch -p1 < ../CVE-2017-9074-ipv6-Prevent-overrun-when-parsing-v6-header-options.patch + cd ${KERNEL_SRC}; patch -p1 < ../CVE-2017-9075-sctp-do-not-inherit-ipv6_-mc-ac-fl-_list-from-parent.patch + cd ${KERNEL_SRC}; patch -p1 < ../CVE-2017-9076_9077-ipv6-dccp-do-not-inherit-ipv6_mc_list-from-parent.patch + cd ${KERNEL_SRC}; patch -p1 < ../CVE-2017-9242-ipv6-fix-out-of-bound-writes-in-__ip6_append_data.patch sed -i ${KERNEL_SRC}/Makefile -e 's/^EXTRAVERSION.*$$/EXTRAVERSION=${EXTRAVERSION}/' touch $@