Index: usbdevs =================================================================== RCS file: /cvs/src/sys/dev/usb/usbdevs,v retrieving revision 1.581 diff -u -r1.581 usbdevs --- usbdevs 17 Jul 2012 09:46:22 -0000 1.581 +++ usbdevs 9 Mar 2013 10:50:11 -0000 @@ -2743,6 +2743,7 @@ /* Microdia / Sonix Techonology Co., Ltd. products */ product MICRODIA YUREX 0x1010 YUREX product MICRODIA CAM_1 0x62c0 CAM_1 +product MICRODIA TEMPER 0x7401 TEMPer sensor /* Micronet Communications products */ product MICRONET SP128AR 0x0003 SP128AR EtherFast Index: usbdevs.h =================================================================== RCS file: /cvs/src/sys/dev/usb/usbdevs.h,v retrieving revision 1.591 diff -u -r1.591 usbdevs.h --- usbdevs.h 17 Jul 2012 09:48:22 -0000 1.591 +++ usbdevs.h 9 Mar 2013 10:50:14 -0000 @@ -2750,6 +2750,7 @@ /* Microdia / Sonix Techonology Co., Ltd. products */ #define USB_PRODUCT_MICRODIA_YUREX 0x1010 /* YUREX */ #define USB_PRODUCT_MICRODIA_CAM_1 0x62c0 /* CAM_1 */ +#define USB_PRODUCT_MICRODIA_TEMPER 0x7401 /* TEMPer sensor */ /* Micronet Communications products */ #define USB_PRODUCT_MICRONET_SP128AR 0x0003 /* SP128AR EtherFast */ Index: usbdevs_data.h =================================================================== RCS file: /cvs/src/sys/dev/usb/usbdevs_data.h,v retrieving revision 1.585 diff -u -r1.585 usbdevs_data.h --- usbdevs_data.h 17 Jul 2012 09:48:22 -0000 1.585 +++ usbdevs_data.h 9 Mar 2013 10:50:17 -0000 @@ -6570,6 +6570,10 @@ "CAM_1", }, { + USB_VENDOR_MICRODIA, USB_PRODUCT_MICRODIA_TEMPER, + "TEMPer sensor", + }, + { USB_VENDOR_MICRONET, USB_PRODUCT_MICRONET_SP128AR, "SP128AR EtherFast", }, Index: uthum.c =================================================================== RCS file: /cvs/src/sys/dev/usb/uthum.c,v retrieving revision 1.17 diff -u -r1.17 uthum.c --- uthum.c 3 Jul 2011 15:47:17 -0000 1.17 +++ uthum.c 9 Mar 2013 10:50:17 -0000 @@ -105,6 +105,14 @@ { 0x0a, 0x0b, 0x0c, 0x0d, 0x00, 0x00, 0x02, 0x00 }; static uint8_t cmd_query[8] = { 0x0a, 0x0b, 0x0c, 0x0d, 0x00, 0x00, 0x01, 0x00 }; +static uint8_t cmd_init0_gold[2] = + { 0x01, 0x00 }; +static uint8_t cmd_init1_gold[8] = + { 0x01, 0x82, 0x77, 0x01, 0x00, 0x00, 0x00, 0x00 }; +static uint8_t cmd_init2_gold[8] = + { 0x01, 0x86, 0xff, 0x01, 0x00, 0x00, 0x00, 0x00 }; +static uint8_t cmd_query_gold[8] = + { 0x01, 0x80, 0x33, 0x01, 0x00, 0x00, 0x00, 0x00 }; struct uthum_sensor { struct ksensor sensor; @@ -127,6 +135,8 @@ size_t sc_ilen; /* input report length */ size_t sc_olen; /* output report length */ + uint8_t *sc_ibuf; + /* sensor framework */ struct uthum_sensor sc_sensor[UTHUM_MAX_SENSORS]; struct ksensordev sc_sensordev; @@ -136,6 +146,7 @@ const struct usb_devno uthum_devs[] = { /* XXX: various TEMPer variants are using same VID/PID */ { USB_VENDOR_TENX, USB_PRODUCT_TENX_TEMPER}, + { USB_VENDOR_MICRODIA, USB_PRODUCT_MICRODIA_TEMPER}, }; #define uthum_lookup(v, p) usb_lookup(uthum_devs, v, p) @@ -147,6 +158,8 @@ int uthum_issue_cmd(struct uthum_softc *, uint8_t, int); int uthum_read_data(struct uthum_softc *, uint8_t, uint8_t *, size_t, int); int uthum_check_device_info(struct uthum_softc *); +int uthum_read_data_gold(struct uthum_softc *, uint8_t *, size_t); +int uthum_check_device_info_gold(struct uthum_softc *); void uthum_setup_sensors(struct uthum_softc *); void uthum_intr(struct uhidev *, void *, u_int); @@ -205,7 +218,7 @@ struct usb_attach_arg *uaa = aux; struct uhidev_attach_arg *uha = (struct uhidev_attach_arg *)uaa; usbd_device_handle dev = uha->parent->sc_udev; - int i, size, repid; + int i, size, repid, err; void *desc; sc->sc_udev = dev; @@ -219,19 +232,48 @@ sc->sc_ilen = hid_report_size(desc, size, hid_input, repid); sc->sc_olen = hid_report_size(desc, size, hid_output, repid); sc->sc_flen = hid_report_size(desc, size, hid_feature, repid); + sc->sc_ibuf = NULL; printf("\n"); - if (sc->sc_flen < 32) { - /* not sensor interface, just attach */ - return; - } + if (uha->uaa->vendor == USB_VENDOR_TENX && + uha->uaa->product == USB_PRODUCT_TENX_TEMPER) { + if (sc->sc_flen < 32) { + /* not sensor interface, just attach */ + return; + } + + /* sensor data comes from control pipe */ + + /* maybe unsupported device */ + if (uthum_check_device_info(sc) < 0) { + DPRINTF(("uthum: unknown device\n")); + return; + }; + } else if (uha->uaa->vendor == USB_VENDOR_MICRODIA && + uha->uaa->product == USB_PRODUCT_MICRODIA_TEMPER) { + if (sc->sc_flen < 8) { + /* not sensor interface, just attach */ + return; + } + + /* sensor data comes from interrupt pipe */ + err = uhidev_open(&sc->sc_hdev); + if (err) { + printf("uthum: uhidev_open %d\n", err); + return; + } + sc->sc_ibuf = malloc(sc->sc_ilen, M_USBDEV, M_WAITOK); - /* maybe unsupported device */ - if (uthum_check_device_info(sc) < 0) { - DPRINTF(("uthum: unknown device\n")); + /* maybe unsupported device */ + if (uthum_check_device_info_gold(sc) < 0) { + DPRINTF(("uthum: unknown device\n")); + return; + } + } else { + /* unsupported device */ return; - }; + } /* attach sensor */ strlcpy(sc->sc_sensordev.xname, sc->sc_hdev.sc_dev.dv_xname, @@ -280,6 +322,11 @@ sensor_task_unregister(sc->sc_sensortask); } + if (sc->sc_ibuf != NULL) { + free(sc->sc_ibuf, M_USBDEV); + sc->sc_ibuf = NULL; + } + return (rv); } @@ -299,7 +346,15 @@ void uthum_intr(struct uhidev *addr, void *ibuf, u_int len) { - /* do nothing */ + struct uthum_softc *sc = (struct uthum_softc *)addr; +printf("x: %d\n", len); + if (sc->sc_ibuf == NULL) + return; +printf("y: %d\n", len); + /* receive sensor data */ + memcpy(sc->sc_ibuf, ibuf, len); + + return; } int @@ -439,6 +494,96 @@ return 0; }; + +int +uthum_read_data_gold(struct uthum_softc *sc, uint8_t *buf, size_t len) +{ + usb_device_request_t req; + usbd_status error; + + /* if return buffer is null, do nothing */ + if ((buf == NULL) || len == 0) + return 0; + + req.bmRequestType = UT_WRITE_CLASS_INTERFACE; + req.bRequest = UR_SET_REPORT; + USETW(req.wValue, 0x0200); + USETW(req.wIndex, 0); + USETW(req.wLength, sizeof(cmd_query_gold)); + error = usbd_do_request(sc->sc_udev, &req, cmd_query_gold); +printf("f:%d\n",error); + if (error) + return EIO; + tsleep(&sc->sc_ibuf, 0, "uthum", hz); + { +int i; +for (i = 0; i < len; i++) printf("%02x ", sc->sc_ibuf[i]); +printf("\n"); + } + /* get answer */ + // XXX + + return 0; +} + +int +uthum_check_device_info_gold(struct uthum_softc *sc) +{ + usb_device_request_t req; + usbd_status error; + uint8_t buf[8]; + + req.bmRequestType = UT_WRITE_CLASS_INTERFACE; + req.bRequest = UR_SET_REPORT; + USETW(req.wValue, 0x0201); + USETW(req.wIndex, 0x0000); + USETW(req.wLength, sizeof(cmd_init0_gold)); + error = usbd_do_request(sc->sc_udev, &req, cmd_init0_gold); +printf("a:%d\n",error); + if (error) + return EIO; + + req.bmRequestType = UT_WRITE_CLASS_INTERFACE; + req.bRequest = UR_SET_REPORT; + USETW(req.wValue, 0x0200); + USETW(req.wIndex, 0x0001); + USETW(req.wLength, sizeof(cmd_init1_gold)); + error = usbd_do_request(sc->sc_udev, &req, cmd_init1_gold); +printf("b:%d\n",error); + if (error) + return EIO; + tsleep(&sc->sc_ibuf, 0, "uthum", hz); + { +int i; +for (i = 0; i < 8; i++) printf("%02x ", sc->sc_ibuf[i]); +printf("\n"); + } + + req.bmRequestType = UT_WRITE_CLASS_INTERFACE; + req.bRequest = UR_SET_REPORT; + USETW(req.wValue, 0x0200); + USETW(req.wIndex, 0x0001); + USETW(req.wLength, sizeof(cmd_init2_gold)); + error = usbd_do_request(sc->sc_udev, &req, cmd_init2_gold); +printf("c:%d\n",error); + if (error) + return EIO; + + /* data comes twice */ + tsleep(&sc->sc_ibuf, 0, "uthum", hz); + tsleep(&sc->sc_ibuf, 0, "uthum", hz); + { +int i; +for (i = 0; i < 8; i++) printf("%02x ", sc->sc_ibuf[i]); +printf("\n"); + } + + error = uthum_read_data_gold(sc, buf, sizeof(buf)); + if (error) + return EIO; + + return 0; +} void uthum_setup_sensors(struct uthum_softc *sc)