From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from mailman by lists.gnu.org with tmda-scanned (Exim 4.43) id 1KWPbo-0004mP-VS for qemu-devel@nongnu.org; Fri, 22 Aug 2008 01:54:53 -0400 Received: from exim by lists.gnu.org with spam-scanned (Exim 4.43) id 1KWPbn-0004m8-Oy for qemu-devel@nongnu.org; Fri, 22 Aug 2008 01:54:52 -0400 Received: from [199.232.76.173] (port=55291 helo=monty-python.gnu.org) by lists.gnu.org with esmtp (Exim 4.43) id 1KWPbn-0004m5-If for qemu-devel@nongnu.org; Fri, 22 Aug 2008 01:54:51 -0400 Received: from hera.kernel.org ([140.211.167.34]:59577) by monty-python.gnu.org with esmtps (TLS-1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.60) (envelope-from ) id 1KWPbm-0006l4-Sq for qemu-devel@nongnu.org; Fri, 22 Aug 2008 01:54:51 -0400 From: Max Krasnyansky Date: Fri, 22 Aug 2008 05:54:31 +0000 Message-Id: <1219384471-6335-1-git-send-email-maxk@kernel.org> Subject: [Qemu-devel] [PATCH] uhci: Fixed length handling for SETUP and OUT tokens Reply-To: qemu-devel@nongnu.org List-Id: qemu-devel.nongnu.org List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: anthony@codemonkey.ws, qemu-devel@nongnu.org Cc: aurelien@aurel32.net, kvm@vger.kernel.org, Max Krasnyansky Fixes regression reported agains Linux 2.6.18. Looks like XP and newer Linux kernels are less sensitive to length returned for control transfers. Signed-off-by: Max Krasnyansky --- hw/usb-uhci.c | 19 ++++++++++--------- 1 files changed, 10 insertions(+), 9 deletions(-) diff --git a/hw/usb-uhci.c b/hw/usb-uhci.c index 0714520..86b4696 100644 --- a/hw/usb-uhci.c +++ b/hw/usb-uhci.c @@ -651,7 +651,7 @@ static int uhci_broadcast_packet(UHCIState *s, USBPacket *p) dprintf("uhci: packet enter. pid %s addr 0x%02x ep %d len %d\n", pid2str(p->pid), p->devaddr, p->devep, p->len); - if (p->pid == USB_TOKEN_OUT) + if (p->pid == USB_TOKEN_OUT || p->pid == USB_TOKEN_SETUP) dump_data(p->data, p->len); ret = USB_RET_NODEV; @@ -771,7 +771,7 @@ out: static int uhci_handle_td(UHCIState *s, uint32_t addr, UHCI_TD *td, uint32_t *int_mask) { UHCIAsync *async; - int len = 0, max_len, ret = 0; + int len = 0, max_len; uint8_t pid; /* Is active ? */ @@ -814,12 +814,13 @@ static int uhci_handle_td(UHCIState *s, uint32_t addr, UHCI_TD *td, uint32_t *in case USB_TOKEN_OUT: case USB_TOKEN_SETUP: cpu_physical_memory_read(td->buffer, async->buffer, max_len); - ret = uhci_broadcast_packet(s, &async->packet); - len = max_len; + len = uhci_broadcast_packet(s, &async->packet); + if (len >= 0) + len = max_len; break; case USB_TOKEN_IN: - ret = uhci_broadcast_packet(s, &async->packet); + len = uhci_broadcast_packet(s, &async->packet); break; default: @@ -830,17 +831,17 @@ static int uhci_handle_td(UHCIState *s, uint32_t addr, UHCI_TD *td, uint32_t *in return -1; } - if (ret == USB_RET_ASYNC) { + if (len == USB_RET_ASYNC) { uhci_async_link(s, async); return 2; } - async->packet.len = ret; + async->packet.len = len; done: - ret = uhci_complete_td(s, td, async, int_mask); + len = uhci_complete_td(s, td, async, int_mask); uhci_async_free(s, async); - return ret; + return len; } static void uhci_async_complete(USBPacket *packet, void *opaque) -- 1.5.5.1