From d9a348501d93c4f768870562e198591d8d629334 Mon Sep 17 00:00:00 2001 From: Greg Kroah-Hartman Date: Tue, 14 Jan 2020 10:41:54 +0100 Subject: [PATCH] 4.4-stable patches added patches: netfilter-arp_tables-init-netns-pointer-in-xt_tgchk_param-struct.patch netfilter-ipset-avoid-null-deref-when-ipset_attr_lineno-is-present.patch usb-fix-don-t-skip-endpoint-descriptors-with-maxpacket-0.patch --- ...tns-pointer-in-xt_tgchk_param-struct.patch | 149 ++++++++++++++++++ ...ef-when-ipset_attr_lineno-is-present.patch | 59 +++++++ queue-4.4/series | 3 + ...ndpoint-descriptors-with-maxpacket-0.patch | 63 ++++++++ 4 files changed, 274 insertions(+) create mode 100644 queue-4.4/netfilter-arp_tables-init-netns-pointer-in-xt_tgchk_param-struct.patch create mode 100644 queue-4.4/netfilter-ipset-avoid-null-deref-when-ipset_attr_lineno-is-present.patch create mode 100644 queue-4.4/usb-fix-don-t-skip-endpoint-descriptors-with-maxpacket-0.patch diff --git a/queue-4.4/netfilter-arp_tables-init-netns-pointer-in-xt_tgchk_param-struct.patch b/queue-4.4/netfilter-arp_tables-init-netns-pointer-in-xt_tgchk_param-struct.patch new file mode 100644 index 00000000000..037d03ba72d --- /dev/null +++ b/queue-4.4/netfilter-arp_tables-init-netns-pointer-in-xt_tgchk_param-struct.patch @@ -0,0 +1,149 @@ +From 1b789577f655060d98d20ed0c6f9fbd469d6ba63 Mon Sep 17 00:00:00 2001 +From: Florian Westphal +Date: Fri, 27 Dec 2019 01:33:10 +0100 +Subject: netfilter: arp_tables: init netns pointer in xt_tgchk_param struct + +From: Florian Westphal + +commit 1b789577f655060d98d20ed0c6f9fbd469d6ba63 upstream. + +We get crash when the targets checkentry function tries to make +use of the network namespace pointer for arptables. + +When the net pointer got added back in 2010, only ip/ip6/ebtables were +changed to initialize it, so arptables has this set to NULL. + +This isn't a problem for normal arptables because no existing +arptables target has a checkentry function that makes use of par->net. + +However, direct users of the setsockopt interface can provide any +target they want as long as its registered for ARP or UNPSEC protocols. + +syzkaller managed to send a semi-valid arptables rule for RATEEST target +which is enough to trigger NULL deref: + +kasan: GPF could be caused by NULL-ptr deref or user memory access +general protection fault: 0000 [#1] PREEMPT SMP KASAN +RIP: xt_rateest_tg_checkentry+0x11d/0xb40 net/netfilter/xt_RATEEST.c:109 +[..] + xt_check_target+0x283/0x690 net/netfilter/x_tables.c:1019 + check_target net/ipv4/netfilter/arp_tables.c:399 [inline] + find_check_entry net/ipv4/netfilter/arp_tables.c:422 [inline] + translate_table+0x1005/0x1d70 net/ipv4/netfilter/arp_tables.c:572 + do_replace net/ipv4/netfilter/arp_tables.c:977 [inline] + do_arpt_set_ctl+0x310/0x640 net/ipv4/netfilter/arp_tables.c:1456 + +Fixes: add67461240c1d ("netfilter: add struct net * to target parameters") +Reported-by: syzbot+d7358a458d8a81aee898@syzkaller.appspotmail.com +Signed-off-by: Florian Westphal +Acked-by: Cong Wang +Signed-off-by: Pablo Neira Ayuso +Signed-off-by: Greg Kroah-Hartman + +--- + net/ipv4/netfilter/arp_tables.c | 27 ++++++++++++++++----------- + 1 file changed, 16 insertions(+), 11 deletions(-) + +--- a/net/ipv4/netfilter/arp_tables.c ++++ b/net/ipv4/netfilter/arp_tables.c +@@ -488,11 +488,12 @@ next: + return 1; + } + +-static inline int check_target(struct arpt_entry *e, const char *name) ++static int check_target(struct arpt_entry *e, struct net *net, const char *name) + { + struct xt_entry_target *t = arpt_get_target(e); + int ret; + struct xt_tgchk_param par = { ++ .net = net, + .table = name, + .entryinfo = e, + .target = t->u.kernel.target, +@@ -510,8 +511,9 @@ static inline int check_target(struct ar + return 0; + } + +-static inline int +-find_check_entry(struct arpt_entry *e, const char *name, unsigned int size, ++static int ++find_check_entry(struct arpt_entry *e, struct net *net, const char *name, ++ unsigned int size, + struct xt_percpu_counter_alloc_state *alloc_state) + { + struct xt_entry_target *t; +@@ -531,7 +533,7 @@ find_check_entry(struct arpt_entry *e, c + } + t->u.kernel.target = target; + +- ret = check_target(e, name); ++ ret = check_target(e, net, name); + if (ret) + goto err; + return 0; +@@ -632,7 +634,9 @@ static inline void cleanup_entry(struct + /* Checks and translates the user-supplied table segment (held in + * newinfo). + */ +-static int translate_table(struct xt_table_info *newinfo, void *entry0, ++static int translate_table(struct net *net, ++ struct xt_table_info *newinfo, ++ void *entry0, + const struct arpt_replace *repl) + { + struct xt_percpu_counter_alloc_state alloc_state = { 0 }; +@@ -709,7 +713,7 @@ static int translate_table(struct xt_tab + /* Finally, each sanity check must pass */ + i = 0; + xt_entry_foreach(iter, entry0, newinfo->size) { +- ret = find_check_entry(iter, repl->name, repl->size, ++ ret = find_check_entry(iter, net, repl->name, repl->size, + &alloc_state); + if (ret != 0) + break; +@@ -1114,7 +1118,7 @@ static int do_replace(struct net *net, c + goto free_newinfo; + } + +- ret = translate_table(newinfo, loc_cpu_entry, &tmp); ++ ret = translate_table(net, newinfo, loc_cpu_entry, &tmp); + if (ret != 0) + goto free_newinfo; + +@@ -1301,7 +1305,8 @@ compat_copy_entry_from_user(struct compa + } + } + +-static int translate_compat_table(struct xt_table_info **pinfo, ++static int translate_compat_table(struct net *net, ++ struct xt_table_info **pinfo, + void **pentry0, + const struct compat_arpt_replace *compatr) + { +@@ -1371,7 +1376,7 @@ static int translate_compat_table(struct + repl.num_counters = 0; + repl.counters = NULL; + repl.size = newinfo->size; +- ret = translate_table(newinfo, entry1, &repl); ++ ret = translate_table(net, newinfo, entry1, &repl); + if (ret) + goto free_newinfo; + +@@ -1426,7 +1431,7 @@ static int compat_do_replace(struct net + goto free_newinfo; + } + +- ret = translate_compat_table(&newinfo, &loc_cpu_entry, &tmp); ++ ret = translate_compat_table(net, &newinfo, &loc_cpu_entry, &tmp); + if (ret != 0) + goto free_newinfo; + +@@ -1696,7 +1701,7 @@ struct xt_table *arpt_register_table(str + loc_cpu_entry = newinfo->entries; + memcpy(loc_cpu_entry, repl->entries, repl->size); + +- ret = translate_table(newinfo, loc_cpu_entry, repl); ++ ret = translate_table(net, newinfo, loc_cpu_entry, repl); + duprintf("arpt_register_table: translate table gives %d\n", ret); + if (ret != 0) + goto out_free; diff --git a/queue-4.4/netfilter-ipset-avoid-null-deref-when-ipset_attr_lineno-is-present.patch b/queue-4.4/netfilter-ipset-avoid-null-deref-when-ipset_attr_lineno-is-present.patch new file mode 100644 index 00000000000..7b9b62d59f4 --- /dev/null +++ b/queue-4.4/netfilter-ipset-avoid-null-deref-when-ipset_attr_lineno-is-present.patch @@ -0,0 +1,59 @@ +From 22dad713b8a5ff488e07b821195270672f486eb2 Mon Sep 17 00:00:00 2001 +From: Florian Westphal +Date: Wed, 8 Jan 2020 10:59:38 +0100 +Subject: netfilter: ipset: avoid null deref when IPSET_ATTR_LINENO is present + +From: Florian Westphal + +commit 22dad713b8a5ff488e07b821195270672f486eb2 upstream. + +The set uadt functions assume lineno is never NULL, but it is in +case of ip_set_utest(). + +syzkaller managed to generate a netlink message that calls this with +LINENO attr present: + +general protection fault: 0000 [#1] PREEMPT SMP KASAN +RIP: 0010:hash_mac4_uadt+0x1bc/0x470 net/netfilter/ipset/ip_set_hash_mac.c:104 +Call Trace: + ip_set_utest+0x55b/0x890 net/netfilter/ipset/ip_set_core.c:1867 + nfnetlink_rcv_msg+0xcf2/0xfb0 net/netfilter/nfnetlink.c:229 + netlink_rcv_skb+0x177/0x450 net/netlink/af_netlink.c:2477 + nfnetlink_rcv+0x1ba/0x460 net/netfilter/nfnetlink.c:563 + +pass a dummy lineno storage, its easier than patching all set +implementations. + +This seems to be a day-0 bug. + +Cc: Jozsef Kadlecsik +Reported-by: syzbot+34bd2369d38707f3f4a7@syzkaller.appspotmail.com +Fixes: a7b4f989a6294 ("netfilter: ipset: IP set core support") +Signed-off-by: Florian Westphal +Acked-by: Jozsef Kadlecsik +Signed-off-by: Pablo Neira Ayuso +Signed-off-by: Greg Kroah-Hartman + +--- + net/netfilter/ipset/ip_set_core.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +--- a/net/netfilter/ipset/ip_set_core.c ++++ b/net/netfilter/ipset/ip_set_core.c +@@ -1619,6 +1619,7 @@ ip_set_utest(struct sock *ctnl, struct s + struct ip_set *set; + struct nlattr *tb[IPSET_ATTR_ADT_MAX + 1] = {}; + int ret = 0; ++ u32 lineno; + + if (unlikely(protocol_failed(attr) || + !attr[IPSET_ATTR_SETNAME] || +@@ -1635,7 +1636,7 @@ ip_set_utest(struct sock *ctnl, struct s + return -IPSET_ERR_PROTOCOL; + + rcu_read_lock_bh(); +- ret = set->variant->uadt(set, tb, IPSET_TEST, NULL, 0, 0); ++ ret = set->variant->uadt(set, tb, IPSET_TEST, &lineno, 0, 0); + rcu_read_unlock_bh(); + /* Userspace can't trigger element to be re-added */ + if (ret == -EAGAIN) diff --git a/queue-4.4/series b/queue-4.4/series index d9e9acf10df..f68b5bc5327 100644 --- a/queue-4.4/series +++ b/queue-4.4/series @@ -23,3 +23,6 @@ mwifiex-fix-possible-heap-overflow-in-mwifiex_process_country_ie.patch mwifiex-pcie-fix-memory-leak-in-mwifiex_pcie_alloc_cmdrsp_buf.patch scsi-bfa-release-allocated-memory-in-case-of-error.patch rtl8xxxu-prevent-leaking-urb.patch +usb-fix-don-t-skip-endpoint-descriptors-with-maxpacket-0.patch +netfilter-arp_tables-init-netns-pointer-in-xt_tgchk_param-struct.patch +netfilter-ipset-avoid-null-deref-when-ipset_attr_lineno-is-present.patch diff --git a/queue-4.4/usb-fix-don-t-skip-endpoint-descriptors-with-maxpacket-0.patch b/queue-4.4/usb-fix-don-t-skip-endpoint-descriptors-with-maxpacket-0.patch new file mode 100644 index 00000000000..8bd93c9ddd3 --- /dev/null +++ b/queue-4.4/usb-fix-don-t-skip-endpoint-descriptors-with-maxpacket-0.patch @@ -0,0 +1,63 @@ +From 2548288b4fb059b2da9ceada172ef763077e8a59 Mon Sep 17 00:00:00 2001 +From: Alan Stern +Date: Mon, 6 Jan 2020 10:43:42 -0500 +Subject: USB: Fix: Don't skip endpoint descriptors with maxpacket=0 + +From: Alan Stern + +commit 2548288b4fb059b2da9ceada172ef763077e8a59 upstream. + +It turns out that even though endpoints with a maxpacket length of 0 +aren't useful for data transfer, the descriptors do serve other +purposes. In particular, skipping them will also skip over other +class-specific descriptors for classes such as UVC. This unexpected +side effect has caused some UVC cameras to stop working. + +In addition, the USB spec requires that when isochronous endpoint +descriptors are present in an interface's altsetting 0 (which is true +on some devices), the maxpacket size _must_ be set to 0. Warning +about such things seems like a bad idea. + +This patch updates an earlier commit which would log a warning and +skip these endpoint descriptors. Now we only log a warning, and we +don't even do that for isochronous endpoints in altsetting 0. + +We don't need to worry about preventing endpoints with maxpacket = 0 +from ever being used for data transfers; usb_submit_urb() already +checks for this. + +Reported-and-tested-by: Roger Whittaker +Fixes: d482c7bb0541 ("USB: Skip endpoints with 0 maxpacket length") +Signed-off-by: Alan Stern +CC: Laurent Pinchart +Link: https://marc.info/?l=linux-usb&m=157790377329882&w=2 +Link: https://lore.kernel.org/r/Pine.LNX.4.44L0.2001061040270.1514-100000@iolanthe.rowland.org +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/usb/core/config.c | 12 ++++++++---- + 1 file changed, 8 insertions(+), 4 deletions(-) + +--- a/drivers/usb/core/config.c ++++ b/drivers/usb/core/config.c +@@ -358,12 +358,16 @@ static int usb_parse_endpoint(struct dev + endpoint->desc.wMaxPacketSize = cpu_to_le16(8); + } + +- /* Validate the wMaxPacketSize field */ ++ /* ++ * Validate the wMaxPacketSize field. ++ * Some devices have isochronous endpoints in altsetting 0; ++ * the USB-2 spec requires such endpoints to have wMaxPacketSize = 0 ++ * (see the end of section 5.6.3), so don't warn about them. ++ */ + maxp = usb_endpoint_maxp(&endpoint->desc); +- if (maxp == 0) { +- dev_warn(ddev, "config %d interface %d altsetting %d endpoint 0x%X has wMaxPacketSize 0, skipping\n", ++ if (maxp == 0 && !(usb_endpoint_xfer_isoc(d) && asnum == 0)) { ++ dev_warn(ddev, "config %d interface %d altsetting %d endpoint 0x%X has invalid wMaxPacketSize 0\n", + cfgno, inum, asnum, d->bEndpointAddress); +- goto skip_to_next_endpoint_or_interface_descriptor; + } + + /* Find the highest legal maxpacket size for this endpoint */ -- 2.47.3