All of lore.kernel.org
 help / color / mirror / Atom feed
From: Lonnie Mendez <lmendez19@austin.rr.com>
To: qemu-devel@nongnu.org
Subject: Re: [Qemu-devel] Large USB patch
Date: Sat, 22 Apr 2006 22:38:31 -0500	[thread overview]
Message-ID: <444AF6B7.1030606@austin.rr.com> (raw)
In-Reply-To: <444A5B65.8010104@gmx.de>

[-- Attachment #1: Type: text/plain, Size: 2442 bytes --]

nix.wie.weg@gmx.de wrote:

>Lonnie Mendez wrote:
>  
>
>>nix.wie.weg@gmx.de wrote:
>>
>>Sorry about that.  I was used to the previous syntax:
>>usb_add host:04b6:0005
>>
>>  My guess is that the new syntax is to distinguish it from the
>>busaddr:addr syntax?  It would seem checking for length would
>>differentiate the two in that case.
>>    
>>
>Yes maybe, but not a real good solution, especially if you know that
>with the solution we have now, you can omit leading zeros.
>  
>
   Aye.

>
>I have attached a small patch, with which you can really add a device to
>a hub, if this is then working is another question, but it should only
>depend on the implementation of usb-hub.c
>  
>
   That works but not in the literal means of the attached device 
actually functioning (see below).  Here is something interesting:

(qemu) usb_add mouse
     Controller 001: uhci
          001:001 = mouse
     Summary: 1 USB Controller, 1 USB Devices
(qemu) usb_add tablet,addto 001:001:001
(qemu) info usb
     Controller 001: uhci
          001:001 = mouse
               001:001:001 = tablet
     Summary: 1 USB Controller, 2 USB Devices
(qemu)

  The device attached on the hub doesn't seem to be receiving 
transactions (like before with the emulated devices):

frame 1227: pid=SETUP addr=0x00 ep=0 len=8
     data_out= 80 06 00 01 00 00 40 00
uhci readw port=0x0002 val=0x0001
uhci writew port=0x0002 val=0x0001
uhci readw port=0x0006 val=0x04cc
frame 1228: pid=SETUP addr=0x00 ep=0 len=8
     data_out= 80 06 00 01 00 00 40 00
frame 1229: pid=SETUP addr=0x00 ep=0 len=8
     data_out= 80 06 00 01 00 00 40 00
uhci readw port=0x0002 val=0x0002
uhci writew port=0x0002 val=0x0002

   There are some problems with the port status request traffic from the 
hub as well:

frame 1174: pid=SETUP addr=0x03 ep=0 len=8
     data_out= 23 03 04 00 01 00 00 00
error usb_generic_handle_packet: unknown USB-Token - 258
     ret=0

   The interface is also giving incorrect errors at certain times:

(qemu) usb_add usbhub
usb_add: extraneous characters at the end of line
(qemu)


   Attached is a patch to get the linux redirector working with the 
changes.  It has a few other modifications as well but nothing radical.  
The default redirector for linux host was changed to the linux 
redirector as well (just a heads up).  I'm still using the libusb 
redirector for testing here but it's good to restore the linux 
redirector as default on linux host.


[-- Attachment #2: lusb-upd4.diff --]
[-- Type: text/plain, Size: 13121 bytes --]

--- a/qemu/configure	2006-04-22 21:58:54.000000000 -0500
+++ b/qemu/configure	2006-04-22 22:00:43.000000000 -0500
@@ -105,7 +105,7 @@
 ;;
 MINGW32*)
 mingw32="yes"
-usb="linux"
+usb="generic"
 ;;
 FreeBSD)
 bsd="yes"
@@ -130,7 +130,7 @@
 oss="yes"
 linux="yes"
 user="yes"
-usb="generic"
+usb="linux"
 if [ "$cpu" = "i386" -o "$cpu" = "x86_64" ] ; then
     kqemu="yes"
 fi
--- a/qemu/usb-linux.c	2006-04-22 21:58:54.000000000 -0500
+++ b/qemu/usb-linux.c	2006-04-22 22:02:10.000000000 -0500
@@ -42,11 +42,14 @@
     void *data;
 };
 
-typedef int USBScanFunc(void *opaque, int bus_num, int addr, int class_id,
+typedef int USBScanFunc(void *opaque, int bus_num, int addr,
                         int vendor_id, int product_id, 
-                        const char *product_name, int speed);
+                        const char *spec_version,
+                        const char *manf_string,
+                        const char *prod_string);
 static int usb_host_find_device(int *pbus_num, int *paddr, 
                                 const char *devname);
+int usb_host_handle_close(USBDevice *opaque);
 
 //#define DEBUG
 
@@ -63,32 +66,19 @@
             "error code:    %i\n", ret );
 # endif
     switch(ret) {
-    case -ETIMEDOUT:
+    case ETIMEDOUT:
 # ifdef DEBUG
         printf( "USB_ERROR: ETIMEDOUT\n" );
 #endif
         return USB_RET_NAK;
         break;
-    case -EIO: 
-# ifdef DEBUG
-        printf( "USB_ERROR: EIO\n" );
-#endif
-        /* stall condition on win32 */
-        /* XXX: clear stall */
-        return USB_RET_STALL;
-        break;
-    case -EBUSY:
-        /* stall on linux */
-        /* XXX: clear stall */
-        return USB_RET_STALL;
-        break;
-    case -EPIPE:
+    case EPIPE:
     default:
         return USB_RET_STALL;
     }
 }
 
-static void usb_host_handle_reset(USBDevice *dev)
+static int usb_host_handle_reset(USBDevice *dev)
 {
 #if 0
     USBHostDevice *s = (USBHostDevice *)dev;
@@ -96,6 +86,7 @@
        done by the host OS */
     ioctl(s->fd, USBDEVFS_RESET);
 #endif
+    return USB_RET_ACK;
 } 
 
 static int usb_host_handle_control(USBDevice *dev,
@@ -118,7 +109,7 @@
     ct.data = data;
     ret = ioctl(s->fd, USBDEVFS_CONTROL, &ct);
     if (ret < 0) {
-        usb_host_handle_error( ret );
+        return usb_host_handle_error( errno );
     } else {
         return ret;
     }
@@ -142,14 +133,14 @@
     bt.data = data;
     ret = ioctl(s->fd, USBDEVFS_BULK, &bt);
     if (ret < 0) {
-        usb_host_handle_error( ret );
+        return usb_host_handle_error( errno );
     } else {
         return ret;
     }
 }
 
 /* XXX: exclude high speed devices or implement EHCI */
-USBDevice *usb_host_device_open(const char *devname)
+USBDevice *usb_host_init(const char *devname)
 {
     int fd, interface, ret, i;
     USBHostDevice *hostdev;
@@ -162,7 +153,7 @@
 
     if (usb_host_find_device(&bus_num, &addr, devname) < 0) 
         return NULL;
-    
+
     snprintf(buf, sizeof(buf), USBDEVFS_PATH "/%03d/%03d", 
              bus_num, addr);
     fd = open(buf, O_RDWR);
@@ -272,12 +263,16 @@
     return q - buf;
 }
 
-void usb_host_device_close(USBDevice *opaque)
+int usb_host_handle_close(USBDevice *opaque)
 {
     USBHostDevice *s = (USBHostDevice *)opaque;
 
-    if (s->fd >= 0)
+    if (s->fd >= 0) {
        close(s->fd);
+       return 1;
+    }
+
+    return -1;
 }
 
 static int usb_host_scan(void *opaque, USBScanFunc *func)
@@ -285,9 +280,11 @@
     FILE *f;
     char line[1024];
     char buf[1024];
-    int bus_num, addr, speed, device_count, class_id, product_id, vendor_id;
+    int bus_num, addr, device_count, product_id, vendor_id;
     int ret;
-    char product_name[512];
+    char manf_name[512];
+    char prod_name[512];
+    char spec_version[6];
     
     f = fopen(USBDEVFS_PATH "/devices", "r");
     if (!f) {
@@ -295,7 +292,7 @@
         return 0;
     }
     device_count = 0;
-    bus_num = addr = speed = class_id = product_id = vendor_id = 0;
+    bus_num = addr = product_id = vendor_id = 0;
     ret = 0;
     for(;;) {
         if (fgets(line, sizeof(line), f) == NULL)
@@ -305,8 +302,8 @@
         if (line[0] == 'T' && line[1] == ':') {
             if (device_count && (vendor_id || product_id)) {
                 /* New device.  Add the previously discovered device.  */
-                ret = func(opaque, bus_num, addr, class_id, vendor_id, 
-                           product_id, product_name, speed);
+                ret = func(opaque, bus_num, addr, vendor_id, product_id,
+                           spec_version, manf_name, prod_name);
                 if (ret)
                     goto the_end;
             }
@@ -316,19 +313,17 @@
             if (get_tag_value(buf, sizeof(buf), line, "Dev#=", " ") < 0)
                 goto fail;
             addr = atoi(buf);
-            if (get_tag_value(buf, sizeof(buf), line, "Spd=", " ") < 0)
-                goto fail;
-            if (!strcmp(buf, "480"))
-                speed = USB_SPEED_HIGH;
-            else if (!strcmp(buf, "1.5"))
-                speed = USB_SPEED_LOW;
-            else
-                speed = USB_SPEED_FULL;
-            product_name[0] = '\0';
-            class_id = 0xff;
+            strcpy(spec_version, "01.10");
+            strcpy(manf_name, "unknown");
+            strcpy(prod_name, "unknown");
             device_count++;
             product_id = 0;
             vendor_id = 0;
+        } else if (line[0] == 'D' && line[1] == ':') {
+            if (get_tag_value(&buf[1], sizeof(buf) - 1, line, "Ver=", " ") < 0)
+                goto fail;
+            buf[0] = '0';
+            pstrcpy(spec_version, sizeof(spec_version), buf);
         } else if (line[0] == 'P' && line[1] == ':') {
             if (get_tag_value(buf, sizeof(buf), line, "Vendor=", " ") < 0)
                 goto fail;
@@ -337,20 +332,22 @@
                 goto fail;
             product_id = strtoul(buf, NULL, 16);
         } else if (line[0] == 'S' && line[1] == ':') {
-            if (get_tag_value(buf, sizeof(buf), line, "Product=", "") < 0)
-                goto fail;
-            pstrcpy(product_name, sizeof(product_name), buf);
-        } else if (line[0] == 'D' && line[1] == ':') {
-            if (get_tag_value(buf, sizeof(buf), line, "Cls=", " (") < 0)
-                goto fail;
-            class_id = strtoul(buf, NULL, 16);
+            if (get_tag_value(buf, sizeof(buf), line, "Manufacturer=", "") < 0) {
+                if (get_tag_value(buf, sizeof(buf), line, "Product=", "") < 0) {
+                    goto fail;
+                } else {
+                    pstrcpy(prod_name, sizeof(prod_name), buf);
+                }
+            } else {
+                pstrcpy(manf_name, sizeof(manf_name), buf);
+            }
         }
     fail: ;
     }
     if (device_count && (vendor_id || product_id)) {
         /* Add the last device.  */
-        ret = func(opaque, bus_num, addr, class_id, vendor_id, 
-                   product_id, product_name, speed);
+        ret = func(opaque, bus_num, addr, vendor_id, product_id, spec_version,
+                   manf_name, prod_name);
     }
  the_end:
     fclose(f);
@@ -364,10 +361,11 @@
     int addr;
 } FindDeviceState;
 
-static int usb_host_find_device_scan(void *opaque, int bus_num, int addr, 
-                                     int class_id,
-                                     int vendor_id, int product_id, 
-                                     const char *product_name, int speed)
+static int usb_host_find_device_scan(void *opaque, int bus_num, int addr,
+                                     int vendor_id, int product_id,
+                                     const char *spec_version,
+                                     const char *manf_string,
+                                     const char *prod_string)
 {
     FindDeviceState *s = opaque;
     if (vendor_id == s->vendor_id &&
@@ -386,108 +384,38 @@
 static int usb_host_find_device(int *pbus_num, int *paddr, 
                                 const char *devname)
 {
-    const char *p;
-    int ret;
     FindDeviceState fs;
 
-    p = strchr(devname, '.');
-    if (p) {
-        *pbus_num = strtoul(devname, NULL, 0);
-        *paddr = strtoul(p + 1, NULL, 0);
-        return 0;
-    }
-    p = strchr(devname, ':');
-    if (p) {
-        fs.vendor_id = strtoul(devname, NULL, 16);
-        fs.product_id = strtoul(p + 1, NULL, 16);
-        ret = usb_host_scan(&fs, usb_host_find_device_scan);
-        if (ret) {
-            *pbus_num = fs.bus_num;
-            *paddr = fs.addr;
-            return 0;
+    if (sscanf(devname, "host:%03d:%03d", pbus_num, paddr) != 2) {
+        if (sscanf(devname, "host:%04xx%04x", &fs.vendor_id, &fs.product_id) == 2) {
+            if (usb_host_scan(&fs, usb_host_find_device_scan)) {
+                *pbus_num = fs.bus_num;
+                *paddr = fs.addr;
+                return 0;
+            } else {
+                return -1;
+            }
+        } else {
+            return -1;
         }
+    } else {
+        return 0;
     }
-    return -1;
 }
 
 /**********************/
 /* USB host device info */
 
-struct usb_class_info {
-    int class;
-    const char *class_name;
-};
-
-static const struct usb_class_info usb_class_info[] = {
-    { USB_CLASS_AUDIO, "Audio"},
-    { USB_CLASS_COMM, "Communication"},
-    { USB_CLASS_HID, "HID"},
-    { USB_CLASS_HUB, "Hub" },
-    { USB_CLASS_PHYSICAL, "Physical" },
-    { USB_CLASS_PRINTER, "Printer" },
-    { USB_CLASS_MASS_STORAGE, "Storage" },
-    { USB_CLASS_CDC_DATA, "Data" },
-    { USB_CLASS_APP_SPEC, "Application Specific" },
-    { USB_CLASS_VENDOR_SPEC, "Vendor Specific" },
-    { USB_CLASS_STILL_IMAGE, "Still Image" },
-    { USB_CLASS_CSCID, 	"Smart Card" },
-    { USB_CLASS_CONTENT_SEC, "Content Security" },
-    { -1, NULL }
-};
-
-static const char *usb_class_str(uint8_t class)
-{
-    const struct usb_class_info *p;
-    for(p = usb_class_info; p->class != -1; p++) {
-        if (p->class == class)
-            break;
-    }
-    return p->class_name;
-}
-
-void usb_info_device(int bus_num, int addr, int class_id,
-                     int vendor_id, int product_id, 
-                     const char *product_name,
-                     int speed)
-{
-    const char *class_str, *speed_str;
-
-    switch(speed) {
-    case USB_SPEED_LOW: 
-        speed_str = "1.5"; 
-        break;
-    case USB_SPEED_FULL: 
-        speed_str = "12"; 
-        break;
-    case USB_SPEED_HIGH: 
-        speed_str = "480"; 
-        break;
-    default:
-        speed_str = "?"; 
-        break;
-    }
-
-    term_printf("  Device %d.%d, speed %s Mb/s\n", 
-                bus_num, addr, speed_str);
-    class_str = usb_class_str(class_id);
-    if (class_str) 
-        term_printf("    %s:", class_str);
-    else
-        term_printf("    Class %02x:", class_id);
-    term_printf(" USB device %04x:%04x", vendor_id, product_id);
-    if (product_name[0] != '\0')
-        term_printf(", %s", product_name);
-    term_printf("\n");
-}
-
 static int usb_host_info_device(void *opaque, int bus_num, int addr, 
-                                int class_id,
-                                int vendor_id, int product_id, 
-                                const char *product_name,
-                                int speed)
-{
-    usb_info_device(bus_num, addr, class_id, vendor_id, product_id,
-                    product_name, speed);
+                                int vendor_id, int product_id,
+                                const char *spec_ver,
+                                const char *manf_string,
+                                const char *prod_string)
+{
+    term_printf("  Device host:%03d:%03d, Manufacturer %s, Product %s\n",
+                bus_num, addr, manf_string, prod_string );
+    term_printf("     VendorID:ProductID %04xx%04x, USB-Standard: %s\n",
+                vendor_id, product_id, spec_ver );
     return 0;
 }
 
--- a/qemu/usb-libusb.c	2006-04-22 21:59:14.000000000 -0500
+++ b/qemu/usb-libusb.c	2006-04-22 22:03:02.000000000 -0500
@@ -368,12 +368,7 @@
 /**********************/
 /* USB host device info */
 
-struct usb_class_info {
-    int class;
-    const char *class_name;
-};
 
- 
 void usb_host_info_device( struct usb_bus *bus, struct usb_device *dev, struct usb_dev_handle *handle )
 {
     char str1[256], str2[256];
--- a/qemu/hw/usb-hub.c	2006-04-22 21:59:14.000000000 -0500
+++ b/qemu/hw/usb-hub.c	2006-04-22 13:51:23.000000000 -0500
@@ -177,7 +177,7 @@
     int i;
     
     if (dev) {
-         if (portnum >= MAX_PORTS || portnum < 0) {
+         if (portnum >= s->nb_ports || portnum < 0) {
 #ifdef DEBUG        
             printf( "This usb hub port does not exist.\n" );
 #endif
@@ -188,7 +188,7 @@
             printf( "Hub Port %i is allready occupied! \n", portnum );
 #endif
             portnum= -1;
-            for (i= 0; i < MAX_PORTS; i++) {
+            for (i= 0; i < s->nb_ports; i++) {
                 if (s->ports[i].dev == NULL) {
 #ifdef DEBUG
                     printf( "Will use Hub Port %i instead! \n", i );

  reply	other threads:[~2006-04-23  3:38 UTC|newest]

Thread overview: 31+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2006-04-20 19:59 [Qemu-devel] Large USB patch nix.wie.weg
2006-04-21  2:23 ` Lonnie Mendez
2006-04-21  5:59   ` nix.wie.weg
2006-04-21  7:04     ` Lonnie Mendez
2006-04-21 14:53 ` Lonnie Mendez
2006-04-21 15:00   ` Lonnie Mendez
2006-04-21 15:50   ` Lonnie Mendez
2006-04-21 16:19     ` Lonnie Mendez
2006-04-21 16:29       ` nix.wie.weg
2006-04-21 17:28         ` Lonnie Mendez
2006-04-21 18:06           ` Lonnie Mendez
2006-04-21 18:38             ` Lonnie Mendez
2006-04-21 20:50               ` Lonnie Mendez
2006-04-22  9:33                 ` nix.wie.weg
2006-04-22 14:36                   ` Lonnie Mendez
2006-04-22 15:36                     ` nix.wie.weg
2006-04-22 15:38                       ` nix.wie.weg
2006-04-22 16:00                     ` nix.wie.weg
2006-04-22 16:19                       ` Lonnie Mendez
2006-04-22 16:35                         ` nix.wie.weg
2006-04-23  3:38                           ` Lonnie Mendez [this message]
2006-04-23 21:54                             ` nix.wie.weg
2006-04-29  1:03                             ` Lonnie Mendez
2006-04-29  3:29                               ` Lonnie Mendez
2006-04-30  0:46                                 ` Lonnie Mendez
2006-04-30 20:56                                   ` Lonnie Mendez
2006-04-21 16:26     ` nix.wie.weg
2006-04-22 14:15 ` nix.wie.weg
2006-04-23 15:02 ` Fabrice Bellard
2006-04-23 16:11   ` nix.wie.weg
2006-04-24 23:50 ` [Qemu-devel] Update for cvs 2006-04-24 nix.wie.weg

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=444AF6B7.1030606@austin.rr.com \
    --to=lmendez19@austin.rr.com \
    --cc=qemu-devel@nongnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.