summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--0000_README4
-rw-r--r--1250_linux-4.4.251.patch1002
2 files changed, 1006 insertions, 0 deletions
diff --git a/0000_README b/0000_README
index b6783e92..237e54e5 100644
--- a/0000_README
+++ b/0000_README
@@ -1043,6 +1043,10 @@ Patch: 1249_linux-4.4.250.patch
From: http://www.kernel.org
Desc: Linux 4.4.250
+Patch: 1250_linux-4.4.251.patch
+From: http://www.kernel.org
+Desc: Linux 4.4.251
+
Patch: 1500_XATTR_USER_PREFIX.patch
From: https://bugs.gentoo.org/show_bug.cgi?id=470644
Desc: Support for namespace user.pax.* on tmpfs.
diff --git a/1250_linux-4.4.251.patch b/1250_linux-4.4.251.patch
new file mode 100644
index 00000000..3554785d
--- /dev/null
+++ b/1250_linux-4.4.251.patch
@@ -0,0 +1,1002 @@
+diff --git a/Makefile b/Makefile
+index c600c076d2c60..4af4da515593a 100644
+--- a/Makefile
++++ b/Makefile
+@@ -1,6 +1,6 @@
+ VERSION = 4
+ PATCHLEVEL = 4
+-SUBLEVEL = 250
++SUBLEVEL = 251
+ EXTRAVERSION =
+ NAME = Blurry Fish Butt
+
+@@ -349,7 +349,7 @@ OBJDUMP = $(CROSS_COMPILE)objdump
+ AWK = awk
+ GENKSYMS = scripts/genksyms/genksyms
+ INSTALLKERNEL := installkernel
+-DEPMOD = /sbin/depmod
++DEPMOD = depmod
+ PERL = perl
+ PYTHON = python
+ CHECK = sparse
+diff --git a/arch/x86/kernel/cpu/mtrr/generic.c b/arch/x86/kernel/cpu/mtrr/generic.c
+index 55d499593e6a2..e2fa0fcbaa69e 100644
+--- a/arch/x86/kernel/cpu/mtrr/generic.c
++++ b/arch/x86/kernel/cpu/mtrr/generic.c
+@@ -166,9 +166,6 @@ static u8 mtrr_type_lookup_variable(u64 start, u64 end, u64 *partial_end,
+ *repeat = 0;
+ *uniform = 1;
+
+- /* Make end inclusive instead of exclusive */
+- end--;
+-
+ prev_match = MTRR_TYPE_INVALID;
+ for (i = 0; i < num_var_ranges; ++i) {
+ unsigned short start_state, end_state, inclusive;
+@@ -260,6 +257,9 @@ u8 mtrr_type_lookup(u64 start, u64 end, u8 *uniform)
+ int repeat;
+ u64 partial_end;
+
++ /* Make end inclusive instead of exclusive */
++ end--;
++
+ if (!mtrr_state_set)
+ return MTRR_TYPE_INVALID;
+
+diff --git a/arch/x86/mm/pgtable.c b/arch/x86/mm/pgtable.c
+index 3ed4753280aaf..289518bb0e8d7 100644
+--- a/arch/x86/mm/pgtable.c
++++ b/arch/x86/mm/pgtable.c
+@@ -720,6 +720,8 @@ int pud_free_pmd_page(pud_t *pud, unsigned long addr)
+ }
+
+ free_page((unsigned long)pmd_sv);
++
++ pgtable_pmd_page_dtor(virt_to_page(pmd));
+ free_page((unsigned long)pmd);
+
+ return 1;
+diff --git a/drivers/atm/idt77252.c b/drivers/atm/idt77252.c
+index 074616b39f4d5..89adb49e435ef 100644
+--- a/drivers/atm/idt77252.c
++++ b/drivers/atm/idt77252.c
+@@ -3615,7 +3615,7 @@ static int idt77252_init_one(struct pci_dev *pcidev,
+
+ if ((err = dma_set_mask_and_coherent(&pcidev->dev, DMA_BIT_MASK(32)))) {
+ printk("idt77252: can't enable DMA for PCI device at %s\n", pci_name(pcidev));
+- return err;
++ goto err_out_disable_pdev;
+ }
+
+ card = kzalloc(sizeof(struct idt77252_dev), GFP_KERNEL);
+diff --git a/drivers/base/core.c b/drivers/base/core.c
+index 92fa2bfa2925d..7e419aaf3c244 100644
+--- a/drivers/base/core.c
++++ b/drivers/base/core.c
+@@ -2357,7 +2357,7 @@ void set_primary_fwnode(struct device *dev, struct fwnode_handle *fwnode)
+ if (fwnode_is_primary(fn)) {
+ dev->fwnode = fn->secondary;
+ if (!(parent && fn == parent->fwnode))
+- fn->secondary = ERR_PTR(-ENODEV);
++ fn->secondary = NULL;
+ } else {
+ dev->fwnode = NULL;
+ }
+diff --git a/drivers/net/ethernet/freescale/ucc_geth.c b/drivers/net/ethernet/freescale/ucc_geth.c
+index 96a1f62cc1484..faf8dfb49fb5d 100644
+--- a/drivers/net/ethernet/freescale/ucc_geth.c
++++ b/drivers/net/ethernet/freescale/ucc_geth.c
+@@ -3934,10 +3934,10 @@ static int ucc_geth_remove(struct platform_device* ofdev)
+ struct ucc_geth_private *ugeth = netdev_priv(dev);
+
+ unregister_netdev(dev);
+- free_netdev(dev);
+ ucc_geth_memclean(ugeth);
+ of_node_put(ugeth->ug_info->tbi_node);
+ of_node_put(ugeth->ug_info->phy_node);
++ free_netdev(dev);
+
+ return 0;
+ }
+diff --git a/drivers/net/ethernet/hisilicon/hns/hns_ethtool.c b/drivers/net/ethernet/hisilicon/hns/hns_ethtool.c
+index a2f2db58b5ab4..82f179b33a807 100644
+--- a/drivers/net/ethernet/hisilicon/hns/hns_ethtool.c
++++ b/drivers/net/ethernet/hisilicon/hns/hns_ethtool.c
+@@ -433,6 +433,10 @@ static void __lb_other_process(struct hns_nic_ring_data *ring_data,
+ /* for mutl buffer*/
+ new_skb = skb_copy(skb, GFP_ATOMIC);
+ dev_kfree_skb_any(skb);
++ if (!new_skb) {
++ netdev_err(ndev, "skb alloc failed\n");
++ return;
++ }
+ skb = new_skb;
+
+ check_ok = 0;
+diff --git a/drivers/net/usb/cdc_ncm.c b/drivers/net/usb/cdc_ncm.c
+index bab13ccfb0850..e9f82b67c7edf 100644
+--- a/drivers/net/usb/cdc_ncm.c
++++ b/drivers/net/usb/cdc_ncm.c
+@@ -1553,9 +1553,6 @@ static void cdc_ncm_status(struct usbnet *dev, struct urb *urb)
+ * USB_CDC_NOTIFY_NETWORK_CONNECTION notification shall be
+ * sent by device after USB_CDC_NOTIFY_SPEED_CHANGE.
+ */
+- netif_info(dev, link, dev->net,
+- "network connection: %sconnected\n",
+- !!event->wValue ? "" : "dis");
+ usbnet_link_change(dev, !!event->wValue, 0);
+ break;
+
+diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c
+index 2759d386ade79..3457842744106 100644
+--- a/drivers/net/virtio_net.c
++++ b/drivers/net/virtio_net.c
+@@ -1372,14 +1372,16 @@ static int virtnet_set_channels(struct net_device *dev,
+
+ get_online_cpus();
+ err = virtnet_set_queues(vi, queue_pairs);
+- if (!err) {
+- netif_set_real_num_tx_queues(dev, queue_pairs);
+- netif_set_real_num_rx_queues(dev, queue_pairs);
+-
+- virtnet_set_affinity(vi);
++ if (err) {
++ put_online_cpus();
++ goto err;
+ }
++ virtnet_set_affinity(vi);
+ put_online_cpus();
+
++ netif_set_real_num_tx_queues(dev, queue_pairs);
++ netif_set_real_num_rx_queues(dev, queue_pairs);
++err:
+ return err;
+ }
+
+diff --git a/drivers/net/wan/hdlc_ppp.c b/drivers/net/wan/hdlc_ppp.c
+index 473a9b8ec9ba5..e38a8dca24cb3 100644
+--- a/drivers/net/wan/hdlc_ppp.c
++++ b/drivers/net/wan/hdlc_ppp.c
+@@ -572,6 +572,13 @@ static void ppp_timer(unsigned long arg)
+ unsigned long flags;
+
+ spin_lock_irqsave(&ppp->lock, flags);
++ /* mod_timer could be called after we entered this function but
++ * before we got the lock.
++ */
++ if (timer_pending(&proto->timer)) {
++ spin_unlock_irqrestore(&ppp->lock, flags);
++ return;
++ }
+ switch (proto->state) {
+ case STOPPING:
+ case REQ_SENT:
+diff --git a/drivers/usb/chipidea/ci_hdrc_imx.c b/drivers/usb/chipidea/ci_hdrc_imx.c
+index 97eb52b976057..8aced1a4a48bc 100644
+--- a/drivers/usb/chipidea/ci_hdrc_imx.c
++++ b/drivers/usb/chipidea/ci_hdrc_imx.c
+@@ -127,9 +127,13 @@ static struct imx_usbmisc_data *usbmisc_get_init_data(struct device *dev)
+ misc_pdev = of_find_device_by_node(args.np);
+ of_node_put(args.np);
+
+- if (!misc_pdev || !platform_get_drvdata(misc_pdev))
++ if (!misc_pdev)
+ return ERR_PTR(-EPROBE_DEFER);
+
++ if (!platform_get_drvdata(misc_pdev)) {
++ put_device(&misc_pdev->dev);
++ return ERR_PTR(-EPROBE_DEFER);
++ }
+ data->dev = &misc_pdev->dev;
+
+ if (of_find_property(np, "disable-over-current", NULL))
+diff --git a/drivers/usb/class/cdc-acm.c b/drivers/usb/class/cdc-acm.c
+index a74a5c0eba6e4..e5ee349a5382b 100644
+--- a/drivers/usb/class/cdc-acm.c
++++ b/drivers/usb/class/cdc-acm.c
+@@ -1894,6 +1894,10 @@ static const struct usb_device_id acm_ids[] = {
+ { USB_DEVICE(0x04d8, 0x0083), /* Bootloader mode */
+ .driver_info = IGNORE_DEVICE,
+ },
++
++ { USB_DEVICE(0x04d8, 0xf58b),
++ .driver_info = IGNORE_DEVICE,
++ },
+ #endif
+
+ /*Samsung phone in firmware update mode */
+diff --git a/drivers/usb/class/usblp.c b/drivers/usb/class/usblp.c
+index 71c2ae4b81067..76701d6ce92c3 100644
+--- a/drivers/usb/class/usblp.c
++++ b/drivers/usb/class/usblp.c
+@@ -289,8 +289,25 @@ static int usblp_ctrl_msg(struct usblp *usblp, int request, int type, int dir, i
+ #define usblp_reset(usblp)\
+ usblp_ctrl_msg(usblp, USBLP_REQ_RESET, USB_TYPE_CLASS, USB_DIR_OUT, USB_RECIP_OTHER, 0, NULL, 0)
+
+-#define usblp_hp_channel_change_request(usblp, channel, buffer) \
+- usblp_ctrl_msg(usblp, USBLP_REQ_HP_CHANNEL_CHANGE_REQUEST, USB_TYPE_VENDOR, USB_DIR_IN, USB_RECIP_INTERFACE, channel, buffer, 1)
++static int usblp_hp_channel_change_request(struct usblp *usblp, int channel, u8 *new_channel)
++{
++ u8 *buf;
++ int ret;
++
++ buf = kzalloc(1, GFP_KERNEL);
++ if (!buf)
++ return -ENOMEM;
++
++ ret = usblp_ctrl_msg(usblp, USBLP_REQ_HP_CHANNEL_CHANGE_REQUEST,
++ USB_TYPE_VENDOR, USB_DIR_IN, USB_RECIP_INTERFACE,
++ channel, buf, 1);
++ if (ret == 0)
++ *new_channel = buf[0];
++
++ kfree(buf);
++
++ return ret;
++}
+
+ /*
+ * See the description for usblp_select_alts() below for the usage
+diff --git a/drivers/usb/gadget/Kconfig b/drivers/usb/gadget/Kconfig
+index 33834aa09ed43..2b1b92b3935bb 100644
+--- a/drivers/usb/gadget/Kconfig
++++ b/drivers/usb/gadget/Kconfig
+@@ -267,6 +267,7 @@ config USB_CONFIGFS_NCM
+ depends on NET
+ select USB_U_ETHER
+ select USB_F_NCM
++ select CRC32
+ help
+ NCM is an advanced protocol for Ethernet encapsulation, allows
+ grouping of several ethernet frames into one USB transfer and
+@@ -316,6 +317,7 @@ config USB_CONFIGFS_EEM
+ depends on NET
+ select USB_U_ETHER
+ select USB_F_EEM
++ select CRC32
+ help
+ CDC EEM is a newer USB standard that is somewhat simpler than CDC ECM
+ and therefore can be supported by more hardware. Technically ECM and
+diff --git a/drivers/usb/gadget/composite.c b/drivers/usb/gadget/composite.c
+index 10f8fde7d6a63..5688df02d9ab9 100644
+--- a/drivers/usb/gadget/composite.c
++++ b/drivers/usb/gadget/composite.c
+@@ -293,8 +293,11 @@ int usb_function_deactivate(struct usb_function *function)
+
+ spin_lock_irqsave(&cdev->lock, flags);
+
+- if (cdev->deactivations == 0)
++ if (cdev->deactivations == 0) {
++ spin_unlock_irqrestore(&cdev->lock, flags);
+ status = usb_gadget_deactivate(cdev->gadget);
++ spin_lock_irqsave(&cdev->lock, flags);
++ }
+ if (status == 0)
+ cdev->deactivations++;
+
+@@ -325,8 +328,11 @@ int usb_function_activate(struct usb_function *function)
+ status = -EINVAL;
+ else {
+ cdev->deactivations--;
+- if (cdev->deactivations == 0)
++ if (cdev->deactivations == 0) {
++ spin_unlock_irqrestore(&cdev->lock, flags);
+ status = usb_gadget_activate(cdev->gadget);
++ spin_lock_irqsave(&cdev->lock, flags);
++ }
+ }
+
+ spin_unlock_irqrestore(&cdev->lock, flags);
+diff --git a/drivers/usb/gadget/configfs.c b/drivers/usb/gadget/configfs.c
+index 5052c11a25205..98f1ce1d61b0b 100644
+--- a/drivers/usb/gadget/configfs.c
++++ b/drivers/usb/gadget/configfs.c
+@@ -1221,9 +1221,9 @@ static void purge_configs_funcs(struct gadget_info *gi)
+
+ cfg = container_of(c, struct config_usb_cfg, c);
+
+- list_for_each_entry_safe(f, tmp, &c->functions, list) {
++ list_for_each_entry_safe_reverse(f, tmp, &c->functions, list) {
+
+- list_move_tail(&f->list, &cfg->func_list);
++ list_move(&f->list, &cfg->func_list);
+ if (f->unbind) {
+ dev_err(&gi->cdev.gadget->dev, "unbind function"
+ " '%s'/%p\n", f->name, f);
+@@ -1507,7 +1507,7 @@ static const struct usb_gadget_driver configfs_driver_template = {
+ .suspend = configfs_composite_suspend,
+ .resume = configfs_composite_resume,
+
+- .max_speed = USB_SPEED_SUPER,
++ .max_speed = USB_SPEED_SUPER_PLUS,
+ .driver = {
+ .owner = THIS_MODULE,
+ .name = "configfs-gadget",
+@@ -1543,7 +1543,7 @@ static struct config_group *gadgets_make(
+ gi->composite.unbind = configfs_do_nothing;
+ gi->composite.suspend = NULL;
+ gi->composite.resume = NULL;
+- gi->composite.max_speed = USB_SPEED_SUPER;
++ gi->composite.max_speed = USB_SPEED_SUPER_PLUS;
+
+ spin_lock_init(&gi->spinlock);
+ mutex_init(&gi->lock);
+diff --git a/drivers/usb/gadget/function/f_printer.c b/drivers/usb/gadget/function/f_printer.c
+index 7b21ef09fffc2..8e32b41fc1297 100644
+--- a/drivers/usb/gadget/function/f_printer.c
++++ b/drivers/usb/gadget/function/f_printer.c
+@@ -1116,6 +1116,7 @@ fail_tx_reqs:
+ printer_req_free(dev->in_ep, req);
+ }
+
++ usb_free_all_descriptors(f);
+ return ret;
+
+ }
+diff --git a/drivers/usb/gadget/function/f_uac2.c b/drivers/usb/gadget/function/f_uac2.c
+index 24c8fbda1a54e..81af315774c62 100644
+--- a/drivers/usb/gadget/function/f_uac2.c
++++ b/drivers/usb/gadget/function/f_uac2.c
+@@ -766,7 +766,7 @@ static struct usb_endpoint_descriptor fs_epout_desc = {
+
+ .bEndpointAddress = USB_DIR_OUT,
+ .bmAttributes = USB_ENDPOINT_XFER_ISOC | USB_ENDPOINT_SYNC_ASYNC,
+- .wMaxPacketSize = cpu_to_le16(1023),
++ /* .wMaxPacketSize = DYNAMIC */
+ .bInterval = 1,
+ };
+
+@@ -775,7 +775,7 @@ static struct usb_endpoint_descriptor hs_epout_desc = {
+ .bDescriptorType = USB_DT_ENDPOINT,
+
+ .bmAttributes = USB_ENDPOINT_XFER_ISOC | USB_ENDPOINT_SYNC_ASYNC,
+- .wMaxPacketSize = cpu_to_le16(1024),
++ /* .wMaxPacketSize = DYNAMIC */
+ .bInterval = 4,
+ };
+
+@@ -843,7 +843,7 @@ static struct usb_endpoint_descriptor fs_epin_desc = {
+
+ .bEndpointAddress = USB_DIR_IN,
+ .bmAttributes = USB_ENDPOINT_XFER_ISOC | USB_ENDPOINT_SYNC_ASYNC,
+- .wMaxPacketSize = cpu_to_le16(1023),
++ /* .wMaxPacketSize = DYNAMIC */
+ .bInterval = 1,
+ };
+
+@@ -852,7 +852,7 @@ static struct usb_endpoint_descriptor hs_epin_desc = {
+ .bDescriptorType = USB_DT_ENDPOINT,
+
+ .bmAttributes = USB_ENDPOINT_XFER_ISOC | USB_ENDPOINT_SYNC_ASYNC,
+- .wMaxPacketSize = cpu_to_le16(1024),
++ /* .wMaxPacketSize = DYNAMIC */
+ .bInterval = 4,
+ };
+
+@@ -963,12 +963,28 @@ free_ep(struct uac2_rtd_params *prm, struct usb_ep *ep)
+ "%s:%d Error!\n", __func__, __LINE__);
+ }
+
+-static void set_ep_max_packet_size(const struct f_uac2_opts *uac2_opts,
++static int set_ep_max_packet_size(const struct f_uac2_opts *uac2_opts,
+ struct usb_endpoint_descriptor *ep_desc,
+- unsigned int factor, bool is_playback)
++ enum usb_device_speed speed, bool is_playback)
+ {
+ int chmask, srate, ssize;
+- u16 max_packet_size;
++ u16 max_size_bw, max_size_ep;
++ unsigned int factor;
++
++ switch (speed) {
++ case USB_SPEED_FULL:
++ max_size_ep = 1023;
++ factor = 1000;
++ break;
++
++ case USB_SPEED_HIGH:
++ max_size_ep = 1024;
++ factor = 8000;
++ break;
++
++ default:
++ return -EINVAL;
++ }
+
+ if (is_playback) {
+ chmask = uac2_opts->p_chmask;
+@@ -980,10 +996,12 @@ static void set_ep_max_packet_size(const struct f_uac2_opts *uac2_opts,
+ ssize = uac2_opts->c_ssize;
+ }
+
+- max_packet_size = num_channels(chmask) * ssize *
++ max_size_bw = num_channels(chmask) * ssize *
+ DIV_ROUND_UP(srate, factor / (1 << (ep_desc->bInterval - 1)));
+- ep_desc->wMaxPacketSize = cpu_to_le16(min_t(u16, max_packet_size,
+- le16_to_cpu(ep_desc->wMaxPacketSize)));
++ ep_desc->wMaxPacketSize = cpu_to_le16(min_t(u16, max_size_bw,
++ max_size_ep));
++
++ return 0;
+ }
+
+ static int
+@@ -1082,10 +1100,33 @@ afunc_bind(struct usb_configuration *cfg, struct usb_function *fn)
+ uac2->c_prm.uac2 = uac2;
+
+ /* Calculate wMaxPacketSize according to audio bandwidth */
+- set_ep_max_packet_size(uac2_opts, &fs_epin_desc, 1000, true);
+- set_ep_max_packet_size(uac2_opts, &fs_epout_desc, 1000, false);
+- set_ep_max_packet_size(uac2_opts, &hs_epin_desc, 8000, true);
+- set_ep_max_packet_size(uac2_opts, &hs_epout_desc, 8000, false);
++ ret = set_ep_max_packet_size(uac2_opts, &fs_epin_desc, USB_SPEED_FULL,
++ true);
++ if (ret < 0) {
++ dev_err(dev, "%s:%d Error!\n", __func__, __LINE__);
++ return ret;
++ }
++
++ ret = set_ep_max_packet_size(uac2_opts, &fs_epout_desc, USB_SPEED_FULL,
++ false);
++ if (ret < 0) {
++ dev_err(dev, "%s:%d Error!\n", __func__, __LINE__);
++ return ret;
++ }
++
++ ret = set_ep_max_packet_size(uac2_opts, &hs_epin_desc, USB_SPEED_HIGH,
++ true);
++ if (ret < 0) {
++ dev_err(dev, "%s:%d Error!\n", __func__, __LINE__);
++ return ret;
++ }
++
++ ret = set_ep_max_packet_size(uac2_opts, &hs_epout_desc, USB_SPEED_HIGH,
++ false);
++ if (ret < 0) {
++ dev_err(dev, "%s:%d Error!\n", __func__, __LINE__);
++ return ret;
++ }
+
+ hs_epout_desc.bEndpointAddress = fs_epout_desc.bEndpointAddress;
+ hs_epin_desc.bEndpointAddress = fs_epin_desc.bEndpointAddress;
+diff --git a/drivers/usb/gadget/legacy/acm_ms.c b/drivers/usb/gadget/legacy/acm_ms.c
+index 64b2cbb0bc6b2..4fe499cf5b770 100644
+--- a/drivers/usb/gadget/legacy/acm_ms.c
++++ b/drivers/usb/gadget/legacy/acm_ms.c
+@@ -207,8 +207,10 @@ static int acm_ms_bind(struct usb_composite_dev *cdev)
+ struct usb_descriptor_header *usb_desc;
+
+ usb_desc = usb_otg_descriptor_alloc(gadget);
+- if (!usb_desc)
++ if (!usb_desc) {
++ status = -ENOMEM;
+ goto fail_string_ids;
++ }
+ usb_otg_descriptor_init(gadget, usb_desc);
+ otg_desc[0] = usb_desc;
+ otg_desc[1] = NULL;
+diff --git a/drivers/usb/host/xhci.c b/drivers/usb/host/xhci.c
+index 51d84332eb786..e7dee8e3ca8b1 100644
+--- a/drivers/usb/host/xhci.c
++++ b/drivers/usb/host/xhci.c
+@@ -4428,19 +4428,19 @@ static u16 xhci_calculate_u1_timeout(struct xhci_hcd *xhci,
+ {
+ unsigned long long timeout_ns;
+
++ if (xhci->quirks & XHCI_INTEL_HOST)
++ timeout_ns = xhci_calculate_intel_u1_timeout(udev, desc);
++ else
++ timeout_ns = udev->u1_params.sel;
++
+ /* Prevent U1 if service interval is shorter than U1 exit latency */
+ if (usb_endpoint_xfer_int(desc) || usb_endpoint_xfer_isoc(desc)) {
+- if (xhci_service_interval_to_ns(desc) <= udev->u1_params.mel) {
++ if (xhci_service_interval_to_ns(desc) <= timeout_ns) {
+ dev_dbg(&udev->dev, "Disable U1, ESIT shorter than exit latency\n");
+ return USB3_LPM_DISABLED;
+ }
+ }
+
+- if (xhci->quirks & XHCI_INTEL_HOST)
+- timeout_ns = xhci_calculate_intel_u1_timeout(udev, desc);
+- else
+- timeout_ns = udev->u1_params.sel;
+-
+ /* The U1 timeout is encoded in 1us intervals.
+ * Don't return a timeout of zero, because that's USB3_LPM_DISABLED.
+ */
+@@ -4492,19 +4492,19 @@ static u16 xhci_calculate_u2_timeout(struct xhci_hcd *xhci,
+ {
+ unsigned long long timeout_ns;
+
++ if (xhci->quirks & XHCI_INTEL_HOST)
++ timeout_ns = xhci_calculate_intel_u2_timeout(udev, desc);
++ else
++ timeout_ns = udev->u2_params.sel;
++
+ /* Prevent U2 if service interval is shorter than U2 exit latency */
+ if (usb_endpoint_xfer_int(desc) || usb_endpoint_xfer_isoc(desc)) {
+- if (xhci_service_interval_to_ns(desc) <= udev->u2_params.mel) {
++ if (xhci_service_interval_to_ns(desc) <= timeout_ns) {
+ dev_dbg(&udev->dev, "Disable U2, ESIT shorter than exit latency\n");
+ return USB3_LPM_DISABLED;
+ }
+ }
+
+- if (xhci->quirks & XHCI_INTEL_HOST)
+- timeout_ns = xhci_calculate_intel_u2_timeout(udev, desc);
+- else
+- timeout_ns = udev->u2_params.sel;
+-
+ /* The U2 timeout is encoded in 256us intervals */
+ timeout_ns = DIV_ROUND_UP_ULL(timeout_ns, 256 * 1000);
+ /* If the necessary timeout value is bigger than what we can set in the
+diff --git a/drivers/usb/misc/yurex.c b/drivers/usb/misc/yurex.c
+index b17aeaafbb7c3..e7761c00eda53 100644
+--- a/drivers/usb/misc/yurex.c
++++ b/drivers/usb/misc/yurex.c
+@@ -515,6 +515,9 @@ static ssize_t yurex_write(struct file *file, const char __user *user_buffer,
+ timeout = schedule_timeout(YUREX_WRITE_TIMEOUT);
+ finish_wait(&dev->waitq, &wait);
+
++ /* make sure URB is idle after timeout or (spurious) CMD_ACK */
++ usb_kill_urb(dev->cntl_urb);
++
+ mutex_unlock(&dev->io_mutex);
+
+ if (retval < 0) {
+diff --git a/drivers/usb/serial/iuu_phoenix.c b/drivers/usb/serial/iuu_phoenix.c
+index 1a966f25b3ef9..ef948285a142d 100644
+--- a/drivers/usb/serial/iuu_phoenix.c
++++ b/drivers/usb/serial/iuu_phoenix.c
+@@ -551,23 +551,29 @@ static int iuu_uart_flush(struct usb_serial_port *port)
+ struct device *dev = &port->dev;
+ int i;
+ int status;
+- u8 rxcmd = IUU_UART_RX;
++ u8 *rxcmd;
+ struct iuu_private *priv = usb_get_serial_port_data(port);
+
+ if (iuu_led(port, 0xF000, 0, 0, 0xFF) < 0)
+ return -EIO;
+
++ rxcmd = kmalloc(1, GFP_KERNEL);
++ if (!rxcmd)
++ return -ENOMEM;
++
++ rxcmd[0] = IUU_UART_RX;
++
+ for (i = 0; i < 2; i++) {
+- status = bulk_immediate(port, &rxcmd, 1);
++ status = bulk_immediate(port, rxcmd, 1);
+ if (status != IUU_OPERATION_OK) {
+ dev_dbg(dev, "%s - uart_flush_write error\n", __func__);
+- return status;
++ goto out_free;
+ }
+
+ status = read_immediate(port, &priv->len, 1);
+ if (status != IUU_OPERATION_OK) {
+ dev_dbg(dev, "%s - uart_flush_read error\n", __func__);
+- return status;
++ goto out_free;
+ }
+
+ if (priv->len > 0) {
+@@ -575,12 +581,16 @@ static int iuu_uart_flush(struct usb_serial_port *port)
+ status = read_immediate(port, priv->buf, priv->len);
+ if (status != IUU_OPERATION_OK) {
+ dev_dbg(dev, "%s - uart_flush_read error\n", __func__);
+- return status;
++ goto out_free;
+ }
+ }
+ }
+ dev_dbg(dev, "%s - uart_flush_read OK!\n", __func__);
+ iuu_led(port, 0, 0xF000, 0, 0xFF);
++
++out_free:
++ kfree(rxcmd);
++
+ return status;
+ }
+
+diff --git a/drivers/usb/serial/keyspan_pda.c b/drivers/usb/serial/keyspan_pda.c
+index e25ea9069350e..c40b64244160b 100644
+--- a/drivers/usb/serial/keyspan_pda.c
++++ b/drivers/usb/serial/keyspan_pda.c
+@@ -559,10 +559,8 @@ exit:
+ static void keyspan_pda_write_bulk_callback(struct urb *urb)
+ {
+ struct usb_serial_port *port = urb->context;
+- struct keyspan_pda_private *priv;
+
+ set_bit(0, &port->write_urbs_free);
+- priv = usb_get_serial_port_data(port);
+
+ /* queue up a wakeup at scheduler time */
+ usb_serial_port_softint(port);
+diff --git a/drivers/usb/serial/option.c b/drivers/usb/serial/option.c
+index 6045a8e24068c..1998b314368e0 100644
+--- a/drivers/usb/serial/option.c
++++ b/drivers/usb/serial/option.c
+@@ -2043,6 +2043,7 @@ static const struct usb_device_id option_ids[] = {
+ { USB_DEVICE_INTERFACE_CLASS(0x2cb7, 0x0105, 0xff), /* Fibocom NL678 series */
+ .driver_info = RSVD(6) },
+ { USB_DEVICE_INTERFACE_CLASS(0x2cb7, 0x01a0, 0xff) }, /* Fibocom NL668-AM/NL652-EU (laptop MBIM) */
++ { USB_DEVICE_INTERFACE_CLASS(0x2df3, 0x9d03, 0xff) }, /* LongSung M5710 */
+ { USB_DEVICE_INTERFACE_CLASS(0x305a, 0x1404, 0xff) }, /* GosunCn GM500 RNDIS */
+ { USB_DEVICE_INTERFACE_CLASS(0x305a, 0x1405, 0xff) }, /* GosunCn GM500 MBIM */
+ { USB_DEVICE_INTERFACE_CLASS(0x305a, 0x1406, 0xff) }, /* GosunCn GM500 ECM/NCM */
+diff --git a/drivers/usb/storage/unusual_uas.h b/drivers/usb/storage/unusual_uas.h
+index b7171c19fca20..7f4245b01baee 100644
+--- a/drivers/usb/storage/unusual_uas.h
++++ b/drivers/usb/storage/unusual_uas.h
+@@ -162,6 +162,13 @@ UNUSUAL_DEV(0x152d, 0x0578, 0x0000, 0x9999,
+ USB_SC_DEVICE, USB_PR_DEVICE, NULL,
+ US_FL_BROKEN_FUA),
+
++/* Reported-by: Thinh Nguyen <thinhn@synopsys.com> */
++UNUSUAL_DEV(0x154b, 0xf00b, 0x0000, 0x9999,
++ "PNY",
++ "Pro Elite SSD",
++ USB_SC_DEVICE, USB_PR_DEVICE, NULL,
++ US_FL_NO_ATA_1X),
++
+ /* Reported-by: Thinh Nguyen <thinhn@synopsys.com> */
+ UNUSUAL_DEV(0x154b, 0xf00d, 0x0000, 0x9999,
+ "PNY",
+diff --git a/drivers/vhost/net.c b/drivers/vhost/net.c
+index 5efac33c29dcb..3c6ca66cb8194 100644
+--- a/drivers/vhost/net.c
++++ b/drivers/vhost/net.c
+@@ -313,6 +313,7 @@ static void handle_tx(struct vhost_net *net)
+ size_t hdr_size;
+ struct socket *sock;
+ struct vhost_net_ubuf_ref *uninitialized_var(ubufs);
++ struct ubuf_info *ubuf;
+ bool zcopy, zcopy_used;
+ int sent_pkts = 0;
+
+@@ -378,9 +379,7 @@ static void handle_tx(struct vhost_net *net)
+
+ /* use msg_control to pass vhost zerocopy ubuf info to skb */
+ if (zcopy_used) {
+- struct ubuf_info *ubuf;
+ ubuf = nvq->ubuf_info + nvq->upend_idx;
+-
+ vq->heads[nvq->upend_idx].id = cpu_to_vhost32(vq, head);
+ vq->heads[nvq->upend_idx].len = VHOST_DMA_IN_PROGRESS;
+ ubuf->callback = vhost_zerocopy_callback;
+@@ -399,7 +398,8 @@ static void handle_tx(struct vhost_net *net)
+ err = sock->ops->sendmsg(sock, &msg, len);
+ if (unlikely(err < 0)) {
+ if (zcopy_used) {
+- vhost_net_ubuf_put(ubufs);
++ if (vq->heads[ubuf->desc].len == VHOST_DMA_IN_PROGRESS)
++ vhost_net_ubuf_put(ubufs);
+ nvq->upend_idx = ((unsigned)nvq->upend_idx - 1)
+ % UIO_MAXIOV;
+ }
+diff --git a/drivers/video/fbdev/hyperv_fb.c b/drivers/video/fbdev/hyperv_fb.c
+index 299412abb1658..883c06381e7c1 100644
+--- a/drivers/video/fbdev/hyperv_fb.c
++++ b/drivers/video/fbdev/hyperv_fb.c
+@@ -713,11 +713,9 @@ static int hvfb_getmem(struct hv_device *hdev, struct fb_info *info)
+ }
+
+ /*
+- * Map the VRAM cacheable for performance. This is also required for
+- * VM Connect to display properly for ARM64 Linux VM, as the host also
+- * maps the VRAM cacheable.
++ * Map the VRAM cacheable for performance.
+ */
+- fb_virt = ioremap_cache(par->mem->start, screen_fb_size);
++ fb_virt = ioremap_wc(par->mem->start, screen_fb_size);
+ if (!fb_virt)
+ goto err2;
+
+diff --git a/include/net/red.h b/include/net/red.h
+index 3618cdfec884e..17821f66de111 100644
+--- a/include/net/red.h
++++ b/include/net/red.h
+@@ -167,12 +167,14 @@ static inline void red_set_vars(struct red_vars *v)
+ v->qcount = -1;
+ }
+
+-static inline bool red_check_params(u32 qth_min, u32 qth_max, u8 Wlog)
++static inline bool red_check_params(u32 qth_min, u32 qth_max, u8 Wlog, u8 Scell_log)
+ {
+ if (fls(qth_min) + Wlog > 32)
+ return false;
+ if (fls(qth_max) + Wlog > 32)
+ return false;
++ if (Scell_log >= 32)
++ return false;
+ if (qth_max < qth_min)
+ return false;
+ return true;
+diff --git a/kernel/workqueue.c b/kernel/workqueue.c
+index 3fb2d45c0b42f..6b293804cd734 100644
+--- a/kernel/workqueue.c
++++ b/kernel/workqueue.c
+@@ -3361,17 +3361,24 @@ static void pwq_adjust_max_active(struct pool_workqueue *pwq)
+ * is updated and visible.
+ */
+ if (!freezable || !workqueue_freezing) {
++ bool kick = false;
++
+ pwq->max_active = wq->saved_max_active;
+
+ while (!list_empty(&pwq->delayed_works) &&
+- pwq->nr_active < pwq->max_active)
++ pwq->nr_active < pwq->max_active) {
+ pwq_activate_first_delayed(pwq);
++ kick = true;
++ }
+
+ /*
+ * Need to kick a worker after thawed or an unbound wq's
+- * max_active is bumped. It's a slow path. Do it always.
++ * max_active is bumped. In realtime scenarios, always kicking a
++ * worker will cause interference on the isolated cpu cores, so
++ * let's kick iff work items were activated.
+ */
+- wake_up_worker(pwq->pool);
++ if (kick)
++ wake_up_worker(pwq->pool);
+ } else {
+ pwq->max_active = 0;
+ }
+diff --git a/lib/genalloc.c b/lib/genalloc.c
+index e3a475b14e260..b8ac0450a2a68 100644
+--- a/lib/genalloc.c
++++ b/lib/genalloc.c
+@@ -83,14 +83,14 @@ static int clear_bits_ll(unsigned long *addr, unsigned long mask_to_clear)
+ * users set the same bit, one user will return remain bits, otherwise
+ * return 0.
+ */
+-static int bitmap_set_ll(unsigned long *map, int start, int nr)
++static int bitmap_set_ll(unsigned long *map, unsigned long start, unsigned long nr)
+ {
+ unsigned long *p = map + BIT_WORD(start);
+- const int size = start + nr;
++ const unsigned long size = start + nr;
+ int bits_to_set = BITS_PER_LONG - (start % BITS_PER_LONG);
+ unsigned long mask_to_set = BITMAP_FIRST_WORD_MASK(start);
+
+- while (nr - bits_to_set >= 0) {
++ while (nr >= bits_to_set) {
+ if (set_bits_ll(p, mask_to_set))
+ return nr;
+ nr -= bits_to_set;
+@@ -118,14 +118,15 @@ static int bitmap_set_ll(unsigned long *map, int start, int nr)
+ * users clear the same bit, one user will return remain bits,
+ * otherwise return 0.
+ */
+-static int bitmap_clear_ll(unsigned long *map, int start, int nr)
++static unsigned long
++bitmap_clear_ll(unsigned long *map, unsigned long start, unsigned long nr)
+ {
+ unsigned long *p = map + BIT_WORD(start);
+- const int size = start + nr;
++ const unsigned long size = start + nr;
+ int bits_to_clear = BITS_PER_LONG - (start % BITS_PER_LONG);
+ unsigned long mask_to_clear = BITMAP_FIRST_WORD_MASK(start);
+
+- while (nr - bits_to_clear >= 0) {
++ while (nr >= bits_to_clear) {
+ if (clear_bits_ll(p, mask_to_clear))
+ return nr;
+ nr -= bits_to_clear;
+@@ -184,8 +185,8 @@ int gen_pool_add_virt(struct gen_pool *pool, unsigned long virt, phys_addr_t phy
+ size_t size, int nid)
+ {
+ struct gen_pool_chunk *chunk;
+- int nbits = size >> pool->min_alloc_order;
+- int nbytes = sizeof(struct gen_pool_chunk) +
++ unsigned long nbits = size >> pool->min_alloc_order;
++ unsigned long nbytes = sizeof(struct gen_pool_chunk) +
+ BITS_TO_LONGS(nbits) * sizeof(long);
+
+ chunk = vzalloc_node(nbytes, nid);
+@@ -242,7 +243,7 @@ void gen_pool_destroy(struct gen_pool *pool)
+ struct list_head *_chunk, *_next_chunk;
+ struct gen_pool_chunk *chunk;
+ int order = pool->min_alloc_order;
+- int bit, end_bit;
++ unsigned long bit, end_bit;
+
+ list_for_each_safe(_chunk, _next_chunk, &pool->chunks) {
+ chunk = list_entry(_chunk, struct gen_pool_chunk, next_chunk);
+@@ -274,7 +275,7 @@ unsigned long gen_pool_alloc(struct gen_pool *pool, size_t size)
+ struct gen_pool_chunk *chunk;
+ unsigned long addr = 0;
+ int order = pool->min_alloc_order;
+- int nbits, start_bit, end_bit, remain;
++ unsigned long nbits, start_bit, end_bit, remain;
+
+ #ifndef CONFIG_ARCH_HAVE_NMI_SAFE_CMPXCHG
+ BUG_ON(in_nmi());
+@@ -357,7 +358,7 @@ void gen_pool_free(struct gen_pool *pool, unsigned long addr, size_t size)
+ {
+ struct gen_pool_chunk *chunk;
+ int order = pool->min_alloc_order;
+- int start_bit, nbits, remain;
++ unsigned long start_bit, nbits, remain;
+
+ #ifndef CONFIG_ARCH_HAVE_NMI_SAFE_CMPXCHG
+ BUG_ON(in_nmi());
+@@ -553,7 +554,7 @@ unsigned long gen_pool_best_fit(unsigned long *map, unsigned long size,
+ index = bitmap_find_next_zero_area(map, size, start, nr, 0);
+
+ while (index < size) {
+- int next_bit = find_next_bit(map, size, index + nr);
++ unsigned long next_bit = find_next_bit(map, size, index + nr);
+ if ((next_bit - index) < len) {
+ len = next_bit - index;
+ start_bit = index;
+diff --git a/net/ipv4/fib_frontend.c b/net/ipv4/fib_frontend.c
+index 7d98aaa3bcade..1a1163cedf17e 100644
+--- a/net/ipv4/fib_frontend.c
++++ b/net/ipv4/fib_frontend.c
+@@ -299,7 +299,7 @@ __be32 fib_compute_spec_dst(struct sk_buff *skb)
+ .flowi4_iif = LOOPBACK_IFINDEX,
+ .flowi4_oif = l3mdev_master_ifindex_rcu(dev),
+ .daddr = ip_hdr(skb)->saddr,
+- .flowi4_tos = RT_TOS(ip_hdr(skb)->tos),
++ .flowi4_tos = ip_hdr(skb)->tos & IPTOS_RT_MASK,
+ .flowi4_scope = scope,
+ .flowi4_mark = vmark ? skb->mark : 0,
+ };
+diff --git a/net/netfilter/ipset/ip_set_hash_gen.h b/net/netfilter/ipset/ip_set_hash_gen.h
+index e5336ab36d679..da0aa720da6fd 100644
+--- a/net/netfilter/ipset/ip_set_hash_gen.h
++++ b/net/netfilter/ipset/ip_set_hash_gen.h
+@@ -113,20 +113,6 @@ htable_size(u8 hbits)
+ return hsize * sizeof(struct hbucket *) + sizeof(struct htable);
+ }
+
+-/* Compute htable_bits from the user input parameter hashsize */
+-static u8
+-htable_bits(u32 hashsize)
+-{
+- /* Assume that hashsize == 2^htable_bits */
+- u8 bits = fls(hashsize - 1);
+-
+- if (jhash_size(bits) != hashsize)
+- /* Round up to the first 2^n value */
+- bits = fls(hashsize);
+-
+- return bits;
+-}
+-
+ #ifdef IP_SET_HASH_WITH_NETS
+ #if IPSET_NET_COUNT > 1
+ #define __CIDR(cidr, i) (cidr[i])
+@@ -1309,7 +1295,11 @@ IPSET_TOKEN(HTYPE, _create)(struct net *net, struct ip_set *set,
+ get_random_bytes(&h->initval, sizeof(h->initval));
+ set->timeout = IPSET_NO_TIMEOUT;
+
+- hbits = htable_bits(hashsize);
++ /* Compute htable_bits from the user input parameter hashsize.
++ * Assume that hashsize == 2^htable_bits,
++ * otherwise round up to the first 2^n value.
++ */
++ hbits = fls(hashsize - 1);
+ hsize = htable_size(hbits);
+ if (hsize == 0) {
+ kfree(h);
+diff --git a/net/netfilter/xt_RATEEST.c b/net/netfilter/xt_RATEEST.c
+index 0be96f8475f74..3b5c76ae43753 100644
+--- a/net/netfilter/xt_RATEEST.c
++++ b/net/netfilter/xt_RATEEST.c
+@@ -107,6 +107,9 @@ static int xt_rateest_tg_checkentry(const struct xt_tgchk_param *par)
+ } cfg;
+ int ret;
+
++ if (strnlen(info->name, sizeof(est->name)) >= sizeof(est->name))
++ return -ENAMETOOLONG;
++
+ if (unlikely(!rnd_inited)) {
+ get_random_bytes(&jhash_rnd, sizeof(jhash_rnd));
+ rnd_inited = true;
+diff --git a/net/sched/sch_choke.c b/net/sched/sch_choke.c
+index 2812de74c9a73..fbdae062b2859 100644
+--- a/net/sched/sch_choke.c
++++ b/net/sched/sch_choke.c
+@@ -439,7 +439,7 @@ static int choke_change(struct Qdisc *sch, struct nlattr *opt)
+
+ ctl = nla_data(tb[TCA_CHOKE_PARMS]);
+
+- if (!red_check_params(ctl->qth_min, ctl->qth_max, ctl->Wlog))
++ if (!red_check_params(ctl->qth_min, ctl->qth_max, ctl->Wlog, ctl->Scell_log))
+ return -EINVAL;
+
+ if (ctl->limit > CHOKE_MAX_QUEUE)
+diff --git a/net/sched/sch_gred.c b/net/sched/sch_gred.c
+index a5745cb2d0145..7af75caf0703d 100644
+--- a/net/sched/sch_gred.c
++++ b/net/sched/sch_gred.c
+@@ -389,7 +389,7 @@ static inline int gred_change_vq(struct Qdisc *sch, int dp,
+ struct gred_sched *table = qdisc_priv(sch);
+ struct gred_sched_data *q = table->tab[dp];
+
+- if (!red_check_params(ctl->qth_min, ctl->qth_max, ctl->Wlog))
++ if (!red_check_params(ctl->qth_min, ctl->qth_max, ctl->Wlog, ctl->Scell_log))
+ return -EINVAL;
+
+ if (!q) {
+diff --git a/net/sched/sch_red.c b/net/sched/sch_red.c
+index 4bf2b599ef98a..842e0b103c3ed 100644
+--- a/net/sched/sch_red.c
++++ b/net/sched/sch_red.c
+@@ -203,7 +203,7 @@ static int red_change(struct Qdisc *sch, struct nlattr *opt)
+ max_P = tb[TCA_RED_MAX_P] ? nla_get_u32(tb[TCA_RED_MAX_P]) : 0;
+
+ ctl = nla_data(tb[TCA_RED_PARMS]);
+- if (!red_check_params(ctl->qth_min, ctl->qth_max, ctl->Wlog))
++ if (!red_check_params(ctl->qth_min, ctl->qth_max, ctl->Wlog, ctl->Scell_log))
+ return -EINVAL;
+
+ if (ctl->limit > 0) {
+diff --git a/net/sched/sch_sfq.c b/net/sched/sch_sfq.c
+index 7929c1a11e123..24cf18ebb8740 100644
+--- a/net/sched/sch_sfq.c
++++ b/net/sched/sch_sfq.c
+@@ -645,7 +645,7 @@ static int sfq_change(struct Qdisc *sch, struct nlattr *opt)
+ }
+
+ if (ctl_v1 && !red_check_params(ctl_v1->qth_min, ctl_v1->qth_max,
+- ctl_v1->Wlog))
++ ctl_v1->Wlog, ctl_v1->Scell_log))
+ return -EINVAL;
+ if (ctl_v1 && ctl_v1->qth_min) {
+ p = kmalloc(sizeof(*p), GFP_KERNEL);
+diff --git a/scripts/depmod.sh b/scripts/depmod.sh
+index baedaef53ca05..b0cb89e73bc56 100755
+--- a/scripts/depmod.sh
++++ b/scripts/depmod.sh
+@@ -14,6 +14,8 @@ if ! test -r System.map ; then
+ exit 0
+ fi
+
++# legacy behavior: "depmod" in /sbin, no /sbin in PATH
++PATH="$PATH:/sbin"
+ if [ -z $(command -v $DEPMOD) ]; then
+ echo "Warning: 'make modules_install' requires $DEPMOD. Please install it." >&2
+ echo "This is probably in the kmod package." >&2
+diff --git a/sound/pci/hda/patch_conexant.c b/sound/pci/hda/patch_conexant.c
+index 3150ddfbdb25e..4c5f703025241 100644
+--- a/sound/pci/hda/patch_conexant.c
++++ b/sound/pci/hda/patch_conexant.c
+@@ -1011,6 +1011,7 @@ static int patch_conexant_auto(struct hda_codec *codec)
+ static const struct hda_device_id snd_hda_id_conexant[] = {
+ HDA_CODEC_ENTRY(0x14f11f86, "CX8070", patch_conexant_auto),
+ HDA_CODEC_ENTRY(0x14f12008, "CX8200", patch_conexant_auto),
++ HDA_CODEC_ENTRY(0x14f120d0, "CX11970", patch_conexant_auto),
+ HDA_CODEC_ENTRY(0x14f15045, "CX20549 (Venice)", patch_conexant_auto),
+ HDA_CODEC_ENTRY(0x14f15047, "CX20551 (Waikiki)", patch_conexant_auto),
+ HDA_CODEC_ENTRY(0x14f15051, "CX20561 (Hermosa)", patch_conexant_auto),
+diff --git a/sound/usb/midi.c b/sound/usb/midi.c
+index 934540042bc2e..df6fde6fd2b6b 100644
+--- a/sound/usb/midi.c
++++ b/sound/usb/midi.c
+@@ -1865,6 +1865,8 @@ static int snd_usbmidi_get_ms_info(struct snd_usb_midi *umidi,
+ ms_ep = find_usb_ms_endpoint_descriptor(hostep);
+ if (!ms_ep)
+ continue;
++ if (ms_ep->bNumEmbMIDIJack > 0x10)
++ continue;
+ if (usb_endpoint_dir_out(ep)) {
+ if (endpoints[epidx].out_ep) {
+ if (++epidx >= MIDI_MAX_ENDPOINTS) {
+@@ -2117,6 +2119,8 @@ static int snd_usbmidi_detect_roland(struct snd_usb_midi *umidi,
+ cs_desc[1] == USB_DT_CS_INTERFACE &&
+ cs_desc[2] == 0xf1 &&
+ cs_desc[3] == 0x02) {
++ if (cs_desc[4] > 0x10 || cs_desc[5] > 0x10)
++ continue;
+ endpoint->in_cables = (1 << cs_desc[4]) - 1;
+ endpoint->out_cables = (1 << cs_desc[5]) - 1;
+ return snd_usbmidi_detect_endpoints(umidi, endpoint, 1);