From 13036c9015b708be424bafbf2d0eca93c4d3e134 Mon Sep 17 00:00:00 2001 From: Greg Kroah-Hartman Date: Mon, 17 Jun 2024 14:18:57 +0200 Subject: [PATCH] 5.15-stable patches added patches: jfs-xattr-fix-buffer-overflow-for-invalid-xattr.patch scsi-mpt3sas-avoid-test-set_bit-operating-in-non-allocated-memory.patch xhci-apply-broken-streams-quirk-to-etron-ej188-xhci-host.patch xhci-apply-reset-resume-quirk-to-etron-ej188-xhci-host.patch xhci-handle-td-clearing-for-multiple-streams-case.patch xhci-set-correct-transferred-length-for-cancelled-bulk-transfers.patch --- ...ix-buffer-overflow-for-invalid-xattr.patch | 40 ++++ ...it-operating-in-non-allocated-memory.patch | 80 +++++++ queue-5.15/series | 6 + ...reams-quirk-to-etron-ej188-xhci-host.patch | 37 ++++ ...esume-quirk-to-etron-ej188-xhci-host.patch | 43 ++++ ...d-clearing-for-multiple-streams-case.patch | 205 ++++++++++++++++++ ...-length-for-cancelled-bulk-transfers.patch | 52 +++++ 7 files changed, 463 insertions(+) create mode 100644 queue-5.15/jfs-xattr-fix-buffer-overflow-for-invalid-xattr.patch create mode 100644 queue-5.15/scsi-mpt3sas-avoid-test-set_bit-operating-in-non-allocated-memory.patch create mode 100644 queue-5.15/xhci-apply-broken-streams-quirk-to-etron-ej188-xhci-host.patch create mode 100644 queue-5.15/xhci-apply-reset-resume-quirk-to-etron-ej188-xhci-host.patch create mode 100644 queue-5.15/xhci-handle-td-clearing-for-multiple-streams-case.patch create mode 100644 queue-5.15/xhci-set-correct-transferred-length-for-cancelled-bulk-transfers.patch diff --git a/queue-5.15/jfs-xattr-fix-buffer-overflow-for-invalid-xattr.patch b/queue-5.15/jfs-xattr-fix-buffer-overflow-for-invalid-xattr.patch new file mode 100644 index 00000000000..fec2ab49ea6 --- /dev/null +++ b/queue-5.15/jfs-xattr-fix-buffer-overflow-for-invalid-xattr.patch @@ -0,0 +1,40 @@ +From 7c55b78818cfb732680c4a72ab270cc2d2ee3d0f Mon Sep 17 00:00:00 2001 +From: Greg Kroah-Hartman +Date: Tue, 14 May 2024 12:06:34 +0200 +Subject: jfs: xattr: fix buffer overflow for invalid xattr + +From: Greg Kroah-Hartman + +commit 7c55b78818cfb732680c4a72ab270cc2d2ee3d0f upstream. + +When an xattr size is not what is expected, it is printed out to the +kernel log in hex format as a form of debugging. But when that xattr +size is bigger than the expected size, printing it out can cause an +access off the end of the buffer. + +Fix this all up by properly restricting the size of the debug hex dump +in the kernel log. + +Reported-by: syzbot+9dfe490c8176301c1d06@syzkaller.appspotmail.com +Cc: Dave Kleikamp +Link: https://lore.kernel.org/r/2024051433-slider-cloning-98f9@gregkh +Signed-off-by: Greg Kroah-Hartman +--- + fs/jfs/xattr.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +--- a/fs/jfs/xattr.c ++++ b/fs/jfs/xattr.c +@@ -557,9 +557,11 @@ static int ea_get(struct inode *inode, s + + size_check: + if (EALIST_SIZE(ea_buf->xattr) != ea_size) { ++ int size = min_t(int, EALIST_SIZE(ea_buf->xattr), ea_size); ++ + printk(KERN_ERR "ea_get: invalid extended attribute\n"); + print_hex_dump(KERN_ERR, "", DUMP_PREFIX_ADDRESS, 16, 1, +- ea_buf->xattr, ea_size, 1); ++ ea_buf->xattr, size, 1); + ea_release(inode, ea_buf); + rc = -EIO; + goto clean_up; diff --git a/queue-5.15/scsi-mpt3sas-avoid-test-set_bit-operating-in-non-allocated-memory.patch b/queue-5.15/scsi-mpt3sas-avoid-test-set_bit-operating-in-non-allocated-memory.patch new file mode 100644 index 00000000000..399fac8637c --- /dev/null +++ b/queue-5.15/scsi-mpt3sas-avoid-test-set_bit-operating-in-non-allocated-memory.patch @@ -0,0 +1,80 @@ +From 4254dfeda82f20844299dca6c38cbffcfd499f41 Mon Sep 17 00:00:00 2001 +From: Breno Leitao +Date: Wed, 5 Jun 2024 01:55:29 -0700 +Subject: scsi: mpt3sas: Avoid test/set_bit() operating in non-allocated memory + +From: Breno Leitao + +commit 4254dfeda82f20844299dca6c38cbffcfd499f41 upstream. + +There is a potential out-of-bounds access when using test_bit() on a single +word. The test_bit() and set_bit() functions operate on long values, and +when testing or setting a single word, they can exceed the word +boundary. KASAN detects this issue and produces a dump: + + BUG: KASAN: slab-out-of-bounds in _scsih_add_device.constprop.0 (./arch/x86/include/asm/bitops.h:60 ./include/asm-generic/bitops/instrumented-atomic.h:29 drivers/scsi/mpt3sas/mpt3sas_scsih.c:7331) mpt3sas + + Write of size 8 at addr ffff8881d26e3c60 by task kworker/u1536:2/2965 + +For full log, please look at [1]. + +Make the allocation at least the size of sizeof(unsigned long) so that +set_bit() and test_bit() have sufficient room for read/write operations +without overwriting unallocated memory. + +[1] Link: https://lore.kernel.org/all/ZkNcALr3W3KGYYJG@gmail.com/ + +Fixes: c696f7b83ede ("scsi: mpt3sas: Implement device_remove_in_progress check in IOCTL path") +Cc: stable@vger.kernel.org +Suggested-by: Keith Busch +Signed-off-by: Breno Leitao +Link: https://lore.kernel.org/r/20240605085530.499432-1-leitao@debian.org +Reviewed-by: Keith Busch +Signed-off-by: Martin K. Petersen +Signed-off-by: Greg Kroah-Hartman +--- + drivers/scsi/mpt3sas/mpt3sas_base.c | 19 +++++++++++++++++++ + 1 file changed, 19 insertions(+) + +--- a/drivers/scsi/mpt3sas/mpt3sas_base.c ++++ b/drivers/scsi/mpt3sas/mpt3sas_base.c +@@ -8337,6 +8337,12 @@ mpt3sas_base_attach(struct MPT3SAS_ADAPT + ioc->pd_handles_sz = (ioc->facts.MaxDevHandle / 8); + if (ioc->facts.MaxDevHandle % 8) + ioc->pd_handles_sz++; ++ /* ++ * pd_handles_sz should have, at least, the minimal room for ++ * set_bit()/test_bit(), otherwise out-of-memory touch may occur. ++ */ ++ ioc->pd_handles_sz = ALIGN(ioc->pd_handles_sz, sizeof(unsigned long)); ++ + ioc->pd_handles = kzalloc(ioc->pd_handles_sz, + GFP_KERNEL); + if (!ioc->pd_handles) { +@@ -8354,6 +8360,13 @@ mpt3sas_base_attach(struct MPT3SAS_ADAPT + ioc->pend_os_device_add_sz = (ioc->facts.MaxDevHandle / 8); + if (ioc->facts.MaxDevHandle % 8) + ioc->pend_os_device_add_sz++; ++ ++ /* ++ * pend_os_device_add_sz should have, at least, the minimal room for ++ * set_bit()/test_bit(), otherwise out-of-memory may occur. ++ */ ++ ioc->pend_os_device_add_sz = ALIGN(ioc->pend_os_device_add_sz, ++ sizeof(unsigned long)); + ioc->pend_os_device_add = kzalloc(ioc->pend_os_device_add_sz, + GFP_KERNEL); + if (!ioc->pend_os_device_add) { +@@ -8645,6 +8658,12 @@ _base_check_ioc_facts_changes(struct MPT + if (ioc->facts.MaxDevHandle % 8) + pd_handles_sz++; + ++ /* ++ * pd_handles should have, at least, the minimal room for ++ * set_bit()/test_bit(), otherwise out-of-memory touch may ++ * occur. ++ */ ++ pd_handles_sz = ALIGN(pd_handles_sz, sizeof(unsigned long)); + pd_handles = krealloc(ioc->pd_handles, pd_handles_sz, + GFP_KERNEL); + if (!pd_handles) { diff --git a/queue-5.15/series b/queue-5.15/series index 74588bf9225..ce7af6379dc 100644 --- a/queue-5.15/series +++ b/queue-5.15/series @@ -87,3 +87,9 @@ nilfs2-fix-nilfs_empty_dir-misjudgment-and-long-loop.patch usb-class-cdc-wdm-fix-cpu-lockup-caused-by-excessive-log-messages.patch usb-typec-tcpm-ignore-received-hard-reset-in-toggling-state.patch mei-me-release-irq-in-mei_me_pci_resume-error-path.patch +jfs-xattr-fix-buffer-overflow-for-invalid-xattr.patch +xhci-set-correct-transferred-length-for-cancelled-bulk-transfers.patch +xhci-apply-reset-resume-quirk-to-etron-ej188-xhci-host.patch +xhci-handle-td-clearing-for-multiple-streams-case.patch +xhci-apply-broken-streams-quirk-to-etron-ej188-xhci-host.patch +scsi-mpt3sas-avoid-test-set_bit-operating-in-non-allocated-memory.patch diff --git a/queue-5.15/xhci-apply-broken-streams-quirk-to-etron-ej188-xhci-host.patch b/queue-5.15/xhci-apply-broken-streams-quirk-to-etron-ej188-xhci-host.patch new file mode 100644 index 00000000000..90dc815cb55 --- /dev/null +++ b/queue-5.15/xhci-apply-broken-streams-quirk-to-etron-ej188-xhci-host.patch @@ -0,0 +1,37 @@ +From 91f7a1524a92c70ffe264db8bdfa075f15bbbeb9 Mon Sep 17 00:00:00 2001 +From: Kuangyi Chiang +Date: Tue, 11 Jun 2024 15:06:09 +0300 +Subject: xhci: Apply broken streams quirk to Etron EJ188 xHCI host + +From: Kuangyi Chiang + +commit 91f7a1524a92c70ffe264db8bdfa075f15bbbeb9 upstream. + +As described in commit 8f873c1ff4ca ("xhci: Blacklist using streams on the +Etron EJ168 controller"), EJ188 have the same issue as EJ168, where Streams +do not work reliable on EJ188. So apply XHCI_BROKEN_STREAMS quirk to EJ188 +as well. + +Cc: stable@vger.kernel.org +Signed-off-by: Kuangyi Chiang +Signed-off-by: Mathias Nyman +Link: https://lore.kernel.org/r/20240611120610.3264502-4-mathias.nyman@linux.intel.com +Signed-off-by: Greg Kroah-Hartman +--- + drivers/usb/host/xhci-pci.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +--- a/drivers/usb/host/xhci-pci.c ++++ b/drivers/usb/host/xhci-pci.c +@@ -278,8 +278,10 @@ static void xhci_pci_quirks(struct devic + xhci->quirks |= XHCI_BROKEN_STREAMS; + } + if (pdev->vendor == PCI_VENDOR_ID_ETRON && +- pdev->device == PCI_DEVICE_ID_EJ188) ++ pdev->device == PCI_DEVICE_ID_EJ188) { + xhci->quirks |= XHCI_RESET_ON_RESUME; ++ xhci->quirks |= XHCI_BROKEN_STREAMS; ++ } + + if (pdev->vendor == PCI_VENDOR_ID_RENESAS && + pdev->device == 0x0014) { diff --git a/queue-5.15/xhci-apply-reset-resume-quirk-to-etron-ej188-xhci-host.patch b/queue-5.15/xhci-apply-reset-resume-quirk-to-etron-ej188-xhci-host.patch new file mode 100644 index 00000000000..a204920af19 --- /dev/null +++ b/queue-5.15/xhci-apply-reset-resume-quirk-to-etron-ej188-xhci-host.patch @@ -0,0 +1,43 @@ +From 17bd54555c2aaecfdb38e2734149f684a73fa584 Mon Sep 17 00:00:00 2001 +From: Kuangyi Chiang +Date: Tue, 11 Jun 2024 15:06:08 +0300 +Subject: xhci: Apply reset resume quirk to Etron EJ188 xHCI host + +From: Kuangyi Chiang + +commit 17bd54555c2aaecfdb38e2734149f684a73fa584 upstream. + +As described in commit c877b3b2ad5c ("xhci: Add reset on resume quirk for +asrock p67 host"), EJ188 have the same issue as EJ168, where completely +dies on resume. So apply XHCI_RESET_ON_RESUME quirk to EJ188 as well. + +Cc: stable@vger.kernel.org +Signed-off-by: Kuangyi Chiang +Signed-off-by: Mathias Nyman +Link: https://lore.kernel.org/r/20240611120610.3264502-3-mathias.nyman@linux.intel.com +Signed-off-by: Greg Kroah-Hartman +--- + drivers/usb/host/xhci-pci.c | 5 +++++ + 1 file changed, 5 insertions(+) + +--- a/drivers/usb/host/xhci-pci.c ++++ b/drivers/usb/host/xhci-pci.c +@@ -36,6 +36,7 @@ + + #define PCI_VENDOR_ID_ETRON 0x1b6f + #define PCI_DEVICE_ID_EJ168 0x7023 ++#define PCI_DEVICE_ID_EJ188 0x7052 + + #define PCI_DEVICE_ID_INTEL_LYNXPOINT_XHCI 0x8c31 + #define PCI_DEVICE_ID_INTEL_LYNXPOINT_LP_XHCI 0x9c31 +@@ -276,6 +277,10 @@ static void xhci_pci_quirks(struct devic + xhci->quirks |= XHCI_TRUST_TX_LENGTH; + xhci->quirks |= XHCI_BROKEN_STREAMS; + } ++ if (pdev->vendor == PCI_VENDOR_ID_ETRON && ++ pdev->device == PCI_DEVICE_ID_EJ188) ++ xhci->quirks |= XHCI_RESET_ON_RESUME; ++ + if (pdev->vendor == PCI_VENDOR_ID_RENESAS && + pdev->device == 0x0014) { + xhci->quirks |= XHCI_TRUST_TX_LENGTH; diff --git a/queue-5.15/xhci-handle-td-clearing-for-multiple-streams-case.patch b/queue-5.15/xhci-handle-td-clearing-for-multiple-streams-case.patch new file mode 100644 index 00000000000..041dbb867a6 --- /dev/null +++ b/queue-5.15/xhci-handle-td-clearing-for-multiple-streams-case.patch @@ -0,0 +1,205 @@ +From 5ceac4402f5d975e5a01c806438eb4e554771577 Mon Sep 17 00:00:00 2001 +From: Hector Martin +Date: Tue, 11 Jun 2024 15:06:10 +0300 +Subject: xhci: Handle TD clearing for multiple streams case + +From: Hector Martin + +commit 5ceac4402f5d975e5a01c806438eb4e554771577 upstream. + +When multiple streams are in use, multiple TDs might be in flight when +an endpoint is stopped. We need to issue a Set TR Dequeue Pointer for +each, to ensure everything is reset properly and the caches cleared. +Change the logic so that any N>1 TDs found active for different streams +are deferred until after the first one is processed, calling +xhci_invalidate_cancelled_tds() again from xhci_handle_cmd_set_deq() to +queue another command until we are done with all of them. Also change +the error/"should never happen" paths to ensure we at least clear any +affected TDs, even if we can't issue a command to clear the hardware +cache, and complain loudly with an xhci_warn() if this ever happens. + +This problem case dates back to commit e9df17eb1408 ("USB: xhci: Correct +assumptions about number of rings per endpoint.") early on in the XHCI +driver's life, when stream support was first added. +It was then identified but not fixed nor made into a warning in commit +674f8438c121 ("xhci: split handling halted endpoints into two steps"), +which added a FIXME comment for the problem case (without materially +changing the behavior as far as I can tell, though the new logic made +the problem more obvious). + +Then later, in commit 94f339147fc3 ("xhci: Fix failure to give back some +cached cancelled URBs."), it was acknowledged again. + +[Mathias: commit 94f339147fc3 ("xhci: Fix failure to give back some cached +cancelled URBs.") was a targeted regression fix to the previously mentioned +patch. Users reported issues with usb stuck after unmounting/disconnecting +UAS devices. This rolled back the TD clearing of multiple streams to its +original state.] + +Apparently the commit author was aware of the problem (yet still chose +to submit it): It was still mentioned as a FIXME, an xhci_dbg() was +added to log the problem condition, and the remaining issue was mentioned +in the commit description. The choice of making the log type xhci_dbg() +for what is, at this point, a completely unhandled and known broken +condition is puzzling and unfortunate, as it guarantees that no actual +users would see the log in production, thereby making it nigh +undebuggable (indeed, even if you turn on DEBUG, the message doesn't +really hint at there being a problem at all). + +It took me *months* of random xHC crashes to finally find a reliable +repro and be able to do a deep dive debug session, which could all have +been avoided had this unhandled, broken condition been actually reported +with a warning, as it should have been as a bug intentionally left in +unfixed (never mind that it shouldn't have been left in at all). + +> Another fix to solve clearing the caches of all stream rings with +> cancelled TDs is needed, but not as urgent. + +3 years after that statement and 14 years after the original bug was +introduced, I think it's finally time to fix it. And maybe next time +let's not leave bugs unfixed (that are actually worse than the original +bug), and let's actually get people to review kernel commits please. + +Fixes xHC crashes and IOMMU faults with UAS devices when handling +errors/faults. Easiest repro is to use `hdparm` to mark an early sector +(e.g. 1024) on a disk as bad, then `cat /dev/sdX > /dev/null` in a loop. +At least in the case of JMicron controllers, the read errors end up +having to cancel two TDs (for two queued requests to different streams) +and the one that didn't get cleared properly ends up faulting the xHC +entirely when it tries to access DMA pages that have since been unmapped, +referred to by the stale TDs. This normally happens quickly (after two +or three loops). After this fix, I left the `cat` in a loop running +overnight and experienced no xHC failures, with all read errors +recovered properly. Repro'd and tested on an Apple M1 Mac Mini +(dwc3 host). + +On systems without an IOMMU, this bug would instead silently corrupt +freed memory, making this a security bug (even on systems with IOMMUs +this could silently corrupt memory belonging to other USB devices on the +same controller, so it's still a security bug). Given that the kernel +autoprobes partition tables, I'm pretty sure a malicious USB device +pretending to be a UAS device and reporting an error with the right +timing could deliberately trigger a UAF and write to freed memory, with +no user action. + +[Mathias: Commit message and code comment edit, original at:] +https://lore.kernel.org/linux-usb/20240524-xhci-streams-v1-1-6b1f13819bea@marcan.st/ + +Fixes: e9df17eb1408 ("USB: xhci: Correct assumptions about number of rings per endpoint.") +Fixes: 94f339147fc3 ("xhci: Fix failure to give back some cached cancelled URBs.") +Fixes: 674f8438c121 ("xhci: split handling halted endpoints into two steps") +Cc: stable@vger.kernel.org +Cc: security@kernel.org +Reviewed-by: Neal Gompa +Signed-off-by: Hector Martin +Signed-off-by: Mathias Nyman +Link: https://lore.kernel.org/r/20240611120610.3264502-5-mathias.nyman@linux.intel.com +Signed-off-by: Greg Kroah-Hartman +--- + drivers/usb/host/xhci-ring.c | 54 ++++++++++++++++++++++++++++++++++--------- + drivers/usb/host/xhci.h | 1 + 2 files changed, 44 insertions(+), 11 deletions(-) + +--- a/drivers/usb/host/xhci-ring.c ++++ b/drivers/usb/host/xhci-ring.c +@@ -994,13 +994,27 @@ static int xhci_invalidate_cancelled_tds + break; + case TD_DIRTY: /* TD is cached, clear it */ + case TD_HALTED: ++ case TD_CLEARING_CACHE_DEFERRED: ++ if (cached_td) { ++ if (cached_td->urb->stream_id != td->urb->stream_id) { ++ /* Multiple streams case, defer move dq */ ++ xhci_dbg(xhci, ++ "Move dq deferred: stream %u URB %p\n", ++ td->urb->stream_id, td->urb); ++ td->cancel_status = TD_CLEARING_CACHE_DEFERRED; ++ break; ++ } ++ ++ /* Should never happen, but clear the TD if it does */ ++ xhci_warn(xhci, ++ "Found multiple active URBs %p and %p in stream %u?\n", ++ td->urb, cached_td->urb, ++ td->urb->stream_id); ++ td_to_noop(xhci, ring, cached_td, false); ++ cached_td->cancel_status = TD_CLEARED; ++ } ++ + td->cancel_status = TD_CLEARING_CACHE; +- if (cached_td) +- /* FIXME stream case, several stopped rings */ +- xhci_dbg(xhci, +- "Move dq past stream %u URB %p instead of stream %u URB %p\n", +- td->urb->stream_id, td->urb, +- cached_td->urb->stream_id, cached_td->urb); + cached_td = td; + break; + } +@@ -1020,10 +1034,16 @@ static int xhci_invalidate_cancelled_tds + if (err) { + /* Failed to move past cached td, just set cached TDs to no-op */ + list_for_each_entry_safe(td, tmp_td, &ep->cancelled_td_list, cancelled_td_list) { +- if (td->cancel_status != TD_CLEARING_CACHE) ++ /* ++ * Deferred TDs need to have the deq pointer set after the above command ++ * completes, so if that failed we just give up on all of them (and ++ * complain loudly since this could cause issues due to caching). ++ */ ++ if (td->cancel_status != TD_CLEARING_CACHE && ++ td->cancel_status != TD_CLEARING_CACHE_DEFERRED) + continue; +- xhci_dbg(xhci, "Failed to clear cancelled cached URB %p, mark clear anyway\n", +- td->urb); ++ xhci_warn(xhci, "Failed to clear cancelled cached URB %p, mark clear anyway\n", ++ td->urb); + td_to_noop(xhci, ring, td, false); + td->cancel_status = TD_CLEARED; + } +@@ -1366,6 +1386,7 @@ static void xhci_handle_cmd_set_deq(stru + struct xhci_ep_ctx *ep_ctx; + struct xhci_slot_ctx *slot_ctx; + struct xhci_td *td, *tmp_td; ++ bool deferred = false; + + ep_index = TRB_TO_EP_INDEX(le32_to_cpu(trb->generic.field[3])); + stream_id = TRB_TO_STREAM_ID(le32_to_cpu(trb->generic.field[2])); +@@ -1452,6 +1473,8 @@ static void xhci_handle_cmd_set_deq(stru + xhci_dbg(ep->xhci, "%s: Giveback cancelled URB %p TD\n", + __func__, td->urb); + xhci_td_cleanup(ep->xhci, td, ep_ring, td->status); ++ } else if (td->cancel_status == TD_CLEARING_CACHE_DEFERRED) { ++ deferred = true; + } else { + xhci_dbg(ep->xhci, "%s: Keep cancelled URB %p TD as cancel_status is %d\n", + __func__, td->urb, td->cancel_status); +@@ -1461,8 +1484,17 @@ cleanup: + ep->ep_state &= ~SET_DEQ_PENDING; + ep->queued_deq_seg = NULL; + ep->queued_deq_ptr = NULL; +- /* Restart any rings with pending URBs */ +- ring_doorbell_for_active_rings(xhci, slot_id, ep_index); ++ ++ if (deferred) { ++ /* We have more streams to clear */ ++ xhci_dbg(ep->xhci, "%s: Pending TDs to clear, continuing with invalidation\n", ++ __func__); ++ xhci_invalidate_cancelled_tds(ep); ++ } else { ++ /* Restart any rings with pending URBs */ ++ xhci_dbg(ep->xhci, "%s: All TDs cleared, ring doorbell\n", __func__); ++ ring_doorbell_for_active_rings(xhci, slot_id, ep_index); ++ } + } + + static void xhci_handle_cmd_reset_ep(struct xhci_hcd *xhci, int slot_id, +--- a/drivers/usb/host/xhci.h ++++ b/drivers/usb/host/xhci.h +@@ -1556,6 +1556,7 @@ enum xhci_cancelled_td_status { + TD_DIRTY = 0, + TD_HALTED, + TD_CLEARING_CACHE, ++ TD_CLEARING_CACHE_DEFERRED, + TD_CLEARED, + }; + diff --git a/queue-5.15/xhci-set-correct-transferred-length-for-cancelled-bulk-transfers.patch b/queue-5.15/xhci-set-correct-transferred-length-for-cancelled-bulk-transfers.patch new file mode 100644 index 00000000000..55b9999e1f4 --- /dev/null +++ b/queue-5.15/xhci-set-correct-transferred-length-for-cancelled-bulk-transfers.patch @@ -0,0 +1,52 @@ +From f0260589b439e2637ad54a2b25f00a516ef28a57 Mon Sep 17 00:00:00 2001 +From: Mathias Nyman +Date: Tue, 11 Jun 2024 15:06:07 +0300 +Subject: xhci: Set correct transferred length for cancelled bulk transfers + +From: Mathias Nyman + +commit f0260589b439e2637ad54a2b25f00a516ef28a57 upstream. + +The transferred length is set incorrectly for cancelled bulk +transfer TDs in case the bulk transfer ring stops on the last transfer +block with a 'Stop - Length Invalid' completion code. + +length essentially ends up being set to the requested length: +urb->actual_length = urb->transfer_buffer_length + +Length for 'Stop - Length Invalid' cases should be the sum of all +TRB transfer block lengths up to the one the ring stopped on, +_excluding_ the one stopped on. + +Fix this by always summing up TRB lengths for 'Stop - Length Invalid' +bulk cases. + +This issue was discovered by Alan Stern while debugging +https://bugzilla.kernel.org/show_bug.cgi?id=218890, but does not +solve that bug. Issue is older than 4.10 kernel but fix won't apply +to those due to major reworks in that area. + +Tested-by: Pierre Tomon +Cc: stable@vger.kernel.org # v4.10+ +Cc: Alan Stern +Signed-off-by: Mathias Nyman +Link: https://lore.kernel.org/r/20240611120610.3264502-2-mathias.nyman@linux.intel.com +Signed-off-by: Greg Kroah-Hartman +--- + drivers/usb/host/xhci-ring.c | 5 ++--- + 1 file changed, 2 insertions(+), 3 deletions(-) + +--- a/drivers/usb/host/xhci-ring.c ++++ b/drivers/usb/host/xhci-ring.c +@@ -2570,9 +2570,8 @@ static int process_bulk_intr_td(struct x + goto finish_td; + case COMP_STOPPED_LENGTH_INVALID: + /* stopped on ep trb with invalid length, exclude it */ +- ep_trb_len = 0; +- remaining = 0; +- break; ++ td->urb->actual_length = sum_trb_lengths(xhci, ep_ring, ep_trb); ++ goto finish_td; + case COMP_USB_TRANSACTION_ERROR: + if (xhci->quirks & XHCI_NO_SOFT_RETRY || + (ep->err_count++ > MAX_SOFT_RETRY) || -- 2.47.3