USB: gadget: android: Support switching vendor ID when configuration changes
authorMike Lockwood <lockwood@android.com>
Wed, 9 Feb 2011 14:38:26 +0000 (09:38 -0500)
committerMike Lockwood <lockwood@android.com>
Wed, 9 Feb 2011 18:01:05 +0000 (13:01 -0500)
Based on the list of enabled USB functions, we can now switch the vendor ID
as well as the product ID.

Signed-off-by: Mike Lockwood <lockwood@android.com>
drivers/usb/gadget/android.c
include/linux/usb/android_composite.h

index 213e8a2d78258e951874fea573982342167749cc..8e6cafc851cb43d6e58c538b2ff9b229427dbc32 100644 (file)
@@ -65,6 +65,7 @@ struct android_dev {
        int num_functions;
        char **functions;
 
+       int vendor_id;
        int product_id;
        int version;
 };
@@ -255,6 +256,22 @@ static int product_matches_functions(struct android_usb_product *p)
        return 1;
 }
 
+static int get_vendor_id(struct android_dev *dev)
+{
+       struct android_usb_product *p = dev->products;
+       int count = dev->num_products;
+       int i;
+
+       if (p) {
+               for (i = 0; i < count; i++, p++) {
+                       if (p->vendor_id && product_matches_functions(p))
+                               return p->vendor_id;
+               }
+       }
+       /* use default vendor ID */
+       return dev->vendor_id;
+}
+
 static int get_product_id(struct android_dev *dev)
 {
        struct android_usb_product *p = dev->products;
@@ -275,7 +292,7 @@ static int android_bind(struct usb_composite_dev *cdev)
 {
        struct android_dev *dev = _android_dev;
        struct usb_gadget       *gadget = cdev->gadget;
-       int                     gcnum, id, product_id, ret;
+       int                     gcnum, id, ret;
 
        printk(KERN_INFO "android_bind\n");
 
@@ -325,8 +342,8 @@ static int android_bind(struct usb_composite_dev *cdev)
 
        usb_gadget_set_selfpowered(gadget);
        dev->cdev = cdev;
-       product_id = get_product_id(dev);
-       device_desc.idProduct = __constant_cpu_to_le16(product_id);
+       device_desc.idVendor = __constant_cpu_to_le16(get_vendor_id(dev));
+       device_desc.idProduct = __constant_cpu_to_le16(get_product_id(dev));
        cdev->desc.idProduct = device_desc.idProduct;
 
        return 0;
@@ -396,7 +413,6 @@ void android_enable_function(struct usb_function *f, int enable)
 {
        struct android_dev *dev = _android_dev;
        int disable = !enable;
-       int product_id;
 
        if (!!f->disabled != disable) {
                usb_function_set_enabled(f, !disable);
@@ -418,8 +434,8 @@ void android_enable_function(struct usb_function *f, int enable)
 
                update_dev_desc(dev);
 
-               product_id = get_product_id(dev);
-               device_desc.idProduct = __constant_cpu_to_le16(product_id);
+               device_desc.idVendor = __constant_cpu_to_le16(get_vendor_id(dev));
+               device_desc.idProduct = __constant_cpu_to_le16(get_product_id(dev));
                if (dev->cdev)
                        dev->cdev->desc.idProduct = device_desc.idProduct;
                usb_composite_force_reset(dev->cdev);
@@ -438,9 +454,11 @@ static int android_probe(struct platform_device *pdev)
                dev->num_products = pdata->num_products;
                dev->functions = pdata->functions;
                dev->num_functions = pdata->num_functions;
-               if (pdata->vendor_id)
+               if (pdata->vendor_id) {
+                       dev->vendor_id = pdata->vendor_id;
                        device_desc.idVendor =
                                __constant_cpu_to_le16(pdata->vendor_id);
+               }
                if (pdata->product_id) {
                        dev->product_id = pdata->product_id;
                        device_desc.idProduct =
index 62e72e3bd2b6e54c1a8970e01d2eae86172f6ba1..7f9000711f4e3e2001ce46cab5b39afaa6b27ac2 100644 (file)
@@ -27,7 +27,12 @@ struct android_usb_function {
 };
 
 struct android_usb_product {
-       /* Default product ID. */
+       /* Vendor ID for this set of functions.
+        * Default vendor_id in platform data will be used if this is zero.
+        */
+       __u16 vendor_id;
+
+       /* Product ID for this set of functions. */
        __u16 product_id;
 
        /* List of function names associated with this product.