On 05/12/15(Sat) 15:22, Christian Heckendorf wrote: > The previous thread[1] discussing these controllers includes two > patches but they seem to have been merged for the commit in a way > that limits support to only Microsoft controllers. 3rd party Xbox 360 > controllers have their own vendor and product IDs but use the same > subclass and protocol as the Microsoft controllers. > > Here's a diff based on the first patch that will match controllers > and assign the report descriptor more generally using subclass/protocol > rather than vendor/product. Is it more correct to create an array > of known vendors/products and match against a call to usb_lookup()?
It's fine since the same check is used in uhidev_use_rdesc(). Could you try this on a Microsoft controller? Does it still work? Jeremy could you check this out? > > [1] http://marc.info/?l=openbsd-tech&m=138229619410284&w=2 > > Thanks, > Christian > > > Index: uhidev.c > =================================================================== > RCS file: /cvs/src/sys/dev/usb/uhidev.c,v > retrieving revision 1.70 > diff -u -p -r1.70 uhidev.c > --- uhidev.c 28 Feb 2015 08:42:41 -0000 1.70 > +++ uhidev.c 5 Dec 2015 20:14:49 -0000 > @@ -62,7 +62,10 @@ > #ifndef SMALL_KERNEL > /* Replacement report descriptors for devices shipped with broken ones */ > #include <dev/usb/uhid_rdesc.h> > -int uhidev_use_rdesc(struct uhidev_softc *, int, int, void **, int *); > +int uhidev_use_rdesc(struct uhidev_softc *, usb_interface_descriptor_t *, > + int, int, void **, int *); > +#define UISUBCLASS_XBOX360_CONTROLLER 0x5d > +#define UIPROTO_XBOX360_GAMEPAD 0x01 > #endif /* !SMALL_KERNEL */ > > #define DEVNAME(sc) ((sc)->sc_dev.dv_xname) > @@ -118,10 +121,10 @@ uhidev_match(struct device *parent, void > if (id == NULL) > return (UMATCH_NONE); > #ifndef SMALL_KERNEL > - if (uaa->vendor == USB_VENDOR_MICROSOFT && > - uaa->product == USB_PRODUCT_MICROSOFT_XBOX360_CONTROLLER && > - id->bInterfaceNumber == 0) > - return (UMATCH_VENDOR_PRODUCT); > + if (id->bInterfaceClass == UICLASS_VENDOR && > + id->bInterfaceSubClass == UISUBCLASS_XBOX360_CONTROLLER && > + id->bInterfaceProtocol == UIPROTO_XBOX360_GAMEPAD) > + return (UMATCH_IFACECLASS_IFACESUBCLASS_IFACEPROTO); > #endif /* !SMALL_KERNEL */ > if (id->bInterfaceClass != UICLASS_HID) > return (UMATCH_NONE); > @@ -191,7 +194,7 @@ uhidev_attach(struct device *parent, str > } > > #ifndef SMALL_KERNEL > - if (uhidev_use_rdesc(sc, uaa->vendor, uaa->product, &desc, &size)) > + if (uhidev_use_rdesc(sc, id, uaa->vendor, uaa->product, &desc, &size)) > return; > #endif /* !SMALL_KERNEL */ > > @@ -275,8 +278,8 @@ uhidev_attach(struct device *parent, str > > #ifndef SMALL_KERNEL > int > -uhidev_use_rdesc(struct uhidev_softc *sc, int vendor, int product, > - void **descp, int *sizep) > +uhidev_use_rdesc(struct uhidev_softc *sc, usb_interface_descriptor_t *id, > + int vendor, int product, void **descp, int *sizep) > { > static uByte reportbuf[] = {2, 2}; > const void *descptr = NULL; > @@ -300,8 +303,9 @@ uhidev_use_rdesc(struct uhidev_softc *sc > default: > break; > } > - } else if (vendor == USB_VENDOR_MICROSOFT && > - product == USB_PRODUCT_MICROSOFT_XBOX360_CONTROLLER) { > + } else if ((id->bInterfaceClass == UICLASS_VENDOR && > + id->bInterfaceSubClass == UISUBCLASS_XBOX360_CONTROLLER && > + id->bInterfaceProtocol == UIPROTO_XBOX360_GAMEPAD)) { > /* The Xbox 360 gamepad has no report descriptor. */ > size = sizeof(uhid_xb360gp_report_descr); > descptr = uhid_xb360gp_report_descr; >