qemu/0006-xhci-limit-the-number-of-link-trbs-we-are-willing-to.patch
Cole Robinson 3d039dc5d8 CVE-2017-7718: cirrus: OOB read access issue (bz #1443443)
CVE-2016-9603: cirrus: heap buffer overflow via vnc connection (bz #1432040)
CVE-2017-7377: 9pfs: fix file descriptor leak (bz #1437872)
CVE-2017-7980: cirrus: OOB r/w access issues in bitblt (bz #1444372)
CVE-2017-8112: vmw_pvscsi: infinite loop in pvscsi_log2 (bz #1445622)
CVE-2017-8309: audio: host memory lekage via capture buffer (bz #1446520)
CVE-2017-8379: input: host memory lekage via keyboard events (bz #1446560)
CVE-2017-8380: scsi: megasas: out-of-bounds read in megasas_mmio_write (bz #1446578)
CVE-2017-9060: virtio-gpu: host memory leakage in Virtio GPU device (bz #1452598)
CVE-2017-9310: net: infinite loop in e1000e NIC emulation (bz #1452623)
CVE-2017-9330: usb: ohci: infinite loop due to incorrect return value (bz #1457699)
CVE-2017-9374: usb: ehci host memory leakage during hotunplug (bz #1459137)
CVE-2017-10806: usb-redirect: stack buffer overflow in debug logging (bz #1468497)
2017-07-12 18:19:21 -04:00

66 lines
2.3 KiB
Diff

From: Gerd Hoffmann <kraxel@redhat.com>
Date: Mon, 10 Oct 2016 12:46:22 +0200
Subject: [PATCH] xhci: limit the number of link trbs we are willing to process
Needed to avoid we run in circles forever in case the guest builds
an endless loop with link trbs.
Reported-by: Li Qiang <liqiang6-s@360.cn>
Tested-by: P J P <ppandit@redhat.com>
Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
Message-id: 1476096382-7981-1-git-send-email-kraxel@redhat.com
(cherry picked from commit 05f43d44e4bc26611ce25fd7d726e483f73363ce)
---
hw/usb/hcd-xhci.c | 10 ++++++++++
1 file changed, 10 insertions(+)
diff --git a/hw/usb/hcd-xhci.c b/hw/usb/hcd-xhci.c
index 281a2a59f0..8a9a31a2f7 100644
--- a/hw/usb/hcd-xhci.c
+++ b/hw/usb/hcd-xhci.c
@@ -54,6 +54,8 @@
* to the specs when it gets them */
#define ER_FULL_HACK
+#define TRB_LINK_LIMIT 4
+
#define LEN_CAP 0x40
#define LEN_OPER (0x400 + 0x10 * MAXPORTS)
#define LEN_RUNTIME ((MAXINTRS + 1) * 0x20)
@@ -1000,6 +1002,7 @@ static TRBType xhci_ring_fetch(XHCIState *xhci, XHCIRing *ring, XHCITRB *trb,
dma_addr_t *addr)
{
PCIDevice *pci_dev = PCI_DEVICE(xhci);
+ uint32_t link_cnt = 0;
while (1) {
TRBType type;
@@ -1026,6 +1029,9 @@ static TRBType xhci_ring_fetch(XHCIState *xhci, XHCIRing *ring, XHCITRB *trb,
ring->dequeue += TRB_SIZE;
return type;
} else {
+ if (++link_cnt > TRB_LINK_LIMIT) {
+ return 0;
+ }
ring->dequeue = xhci_mask64(trb->parameter);
if (trb->control & TRB_LK_TC) {
ring->ccs = !ring->ccs;
@@ -1043,6 +1049,7 @@ static int xhci_ring_chain_length(XHCIState *xhci, const XHCIRing *ring)
bool ccs = ring->ccs;
/* hack to bundle together the two/three TDs that make a setup transfer */
bool control_td_set = 0;
+ uint32_t link_cnt = 0;
while (1) {
TRBType type;
@@ -1058,6 +1065,9 @@ static int xhci_ring_chain_length(XHCIState *xhci, const XHCIRing *ring)
type = TRB_TYPE(trb);
if (type == TR_LINK) {
+ if (++link_cnt > TRB_LINK_LIMIT) {
+ return -length;
+ }
dequeue = xhci_mask64(trb.parameter);
if (trb.control & TRB_LK_TC) {
ccs = !ccs;