From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from eggs.gnu.org ([140.186.70.92]:52518) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1RlfQk-0003hK-Kg for qemu-devel@nongnu.org; Fri, 13 Jan 2012 06:36:26 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1RlfQb-0000aH-Jl for qemu-devel@nongnu.org; Fri, 13 Jan 2012 06:36:22 -0500 Received: from mx1.redhat.com ([209.132.183.28]:22340) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1RlfQb-0000Zx-CJ for qemu-devel@nongnu.org; Fri, 13 Jan 2012 06:36:13 -0500 Received: from int-mx09.intmail.prod.int.phx2.redhat.com (int-mx09.intmail.prod.int.phx2.redhat.com [10.5.11.22]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id q0DBaC5i030478 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK) for ; Fri, 13 Jan 2012 06:36:12 -0500 From: Gerd Hoffmann Date: Fri, 13 Jan 2012 11:18:33 +0100 Message-Id: <1326449914-8591-17-git-send-email-kraxel@redhat.com> In-Reply-To: <1326449914-8591-1-git-send-email-kraxel@redhat.com> References: <1326449914-8591-1-git-send-email-kraxel@redhat.com> Subject: [Qemu-devel] [PATCH 16/17] usb-redir: Try to keep our buffer size near the target size List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: qemu-devel@nongnu.org Cc: Hans de Goede , Gerd Hoffmann From: Hans de Goede Before this patch we would allow the (iso) buffer to grow unlimited (and it would under certain circumstances) leading to way too high latencies for iso data streams. Signed-off-by: Hans de Goede Signed-off-by: Gerd Hoffmann --- usb-redir.c | 30 +++++++++++++++++++++++++++--- 1 files changed, 27 insertions(+), 3 deletions(-) diff --git a/usb-redir.c b/usb-redir.c index cdd929a..147e237 100644 --- a/usb-redir.c +++ b/usb-redir.c @@ -61,6 +61,7 @@ struct endp_data { uint8_t interrupt_started; uint8_t interrupt_error; uint8_t bufpq_prefilled; + uint8_t bufpq_dropping_packets; QTAILQ_HEAD(, buf_packet) bufpq; int bufpq_size; int bufpq_target_size; @@ -290,16 +291,34 @@ static void usbredir_cancel_packet(USBDevice *udev, USBPacket *p) } } -static struct buf_packet *bufp_alloc(USBRedirDevice *dev, +static void bufp_alloc(USBRedirDevice *dev, uint8_t *data, int len, int status, uint8_t ep) { - struct buf_packet *bufp = g_malloc(sizeof(struct buf_packet)); + struct buf_packet *bufp; + + if (!dev->endpoint[EP2I(ep)].bufpq_dropping_packets && + dev->endpoint[EP2I(ep)].bufpq_size > + 2 * dev->endpoint[EP2I(ep)].bufpq_target_size) { + DPRINTF("bufpq overflow, dropping packets ep %02X\n", ep); + dev->endpoint[EP2I(ep)].bufpq_dropping_packets = 1; + } + /* Since we're interupting the stream anyways, drop enough packets to get + back to our target buffer size */ + if (dev->endpoint[EP2I(ep)].bufpq_dropping_packets) { + if (dev->endpoint[EP2I(ep)].bufpq_size > + dev->endpoint[EP2I(ep)].bufpq_target_size) { + free(data); + return; + } + dev->endpoint[EP2I(ep)].bufpq_dropping_packets = 0; + } + + bufp = g_malloc(sizeof(struct buf_packet)); bufp->data = data; bufp->len = len; bufp->status = status; QTAILQ_INSERT_TAIL(&dev->endpoint[EP2I(ep)].bufpq, bufp, next); dev->endpoint[EP2I(ep)].bufpq_size++; - return bufp; } static void bufp_free(USBRedirDevice *dev, struct buf_packet *bufp, @@ -379,6 +398,7 @@ static int usbredir_handle_iso_data(USBRedirDevice *dev, USBPacket *p, DPRINTF("iso stream started ep %02X\n", ep); dev->endpoint[EP2I(ep)].iso_started = 1; dev->endpoint[EP2I(ep)].bufpq_prefilled = 0; + dev->endpoint[EP2I(ep)].bufpq_dropping_packets = 0; } if (ep & USB_DIR_IN) { @@ -505,6 +525,10 @@ static int usbredir_handle_interrupt_data(USBRedirDevice *dev, usbredirparser_do_write(dev->parser); DPRINTF("interrupt recv started ep %02X\n", ep); dev->endpoint[EP2I(ep)].interrupt_started = 1; + /* We don't really want to drop interrupt packets ever, but + having some upper limit to how much we buffer is good. */ + dev->endpoint[EP2I(ep)].bufpq_target_size = 1000; + dev->endpoint[EP2I(ep)].bufpq_dropping_packets = 0; } intp = QTAILQ_FIRST(&dev->endpoint[EP2I(ep)].bufpq); -- 1.7.1