greybus: Fix probing of gpbridge devices
authorViresh Kumar <viresh.kumar@linaro.org>
Thu, 12 May 2016 05:56:48 +0000 (11:26 +0530)
committerGreg Kroah-Hartman <gregkh@google.com>
Fri, 13 May 2016 10:39:10 +0000 (12:39 +0200)
The gpbridge core tries to match the driver's id-table against all
CPorts available within the bundle for which the gpbridge bus was
created. The gpbdev here is unique for a cport_desc and only a single
cport_desc->protocol_id should be matched with the driver's id-table.

Fix it.

Tested on EVT 1.5 with a special manifest for GP module, where multiple
CPorts are part of the same Bridged PHY bundle.

Fixes: 75223f666687 ("gpbridge: implement gpbridge "bus" logic")
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Signed-off-by: Greg Kroah-Hartman <gregkh@google.com>
drivers/staging/greybus/gpbridge.c

index 64ab8dd..adb317d 100644 (file)
@@ -57,44 +57,27 @@ static int gpbdev_uevent(struct device *dev, struct kobj_uevent_env *env)
 }
 
 static const struct gpbridge_device_id *
-gpbdev_match_cport(struct greybus_descriptor_cport *cport_desc,
-               const struct gpbridge_device_id *id)
+gpbdev_match_id(struct gpbridge_device *gpbdev, struct gpbridge_driver *gpbdrv)
 {
+       const struct gpbridge_device_id *id = gpbdrv->id_table;
+
        if (!id)
                return NULL;
 
        for (; id->protocol_id; id++)
-               if (id->protocol_id == cport_desc->protocol_id)
+               if (id->protocol_id == gpbdev->cport_desc->protocol_id)
                        return id;
 
        return NULL;
 }
 
-static const struct gpbridge_device_id *gpbdev_match_id(struct gb_bundle *bundle,
-               const struct gpbridge_device_id *id_table)
-{
-       const struct gpbridge_device_id *id;
-       int i;
-
-       if (!id_table || !bundle || bundle->num_cports == 0)
-               return NULL;
-
-       for (i = 0; i < bundle->num_cports; i++) {
-               id = gpbdev_match_cport(&bundle->cport_desc[i], id_table);
-               if (id)
-                       return id;
-       }
-
-       return NULL;
-}
-
 static int gpbdev_match(struct device *dev, struct device_driver *drv)
 {
        struct gpbridge_driver *gpbdrv = to_gpbridge_driver(drv);
        struct gpbridge_device *gpbdev = to_gpbridge_dev(dev);
        const struct gpbridge_device_id *id;
 
-       id = gpbdev_match_id(gpbdev->bundle, gpbdrv->id_table);
+       id = gpbdev_match_id(gpbdev, gpbdrv);
        if (id)
                return 1;
 
@@ -107,7 +90,7 @@ static int gpbdev_probe(struct device *dev)
        struct gpbridge_device *gpbdev = to_gpbridge_dev(dev);
        const struct gpbridge_device_id *id;
 
-       id = gpbdev_match_id(gpbdev->bundle, gpbdrv->id_table);
+       id = gpbdev_match_id(gpbdev, gpbdrv);
        if (!id)
                return -ENODEV;