def __init__(self,
                 path: str,
                 epIn: int,
                 epOut: int,
                 onReceive: Callable[[bytes], None],
                 onReceiveSize: int = 1):
        """Constructor.
		@param path: The device path.
		@param epIn: The endpoint to read data from.
		@param epOut: The endpoint to write data to.
		@param onReceive: A callable taking a received input report as its only argument.
		"""
        if _isDebug():
            log.debug("Opening device %s" % path)
        readPath = "{path}\\{endpoint}".format(path=path, endpoint=epIn)
        writePath = "{path}\\{endpoint}".format(path=path, endpoint=epOut)
        readHandle = CreateFile(readPath, winKernel.GENERIC_READ, 0, None,
                                winKernel.OPEN_EXISTING, FILE_FLAG_OVERLAPPED,
                                None)
        if readHandle == INVALID_HANDLE_VALUE:
            if _isDebug():
                log.debug("Open read handle failed: %s" % ctypes.WinError())
            raise ctypes.WinError()
        writeHandle = CreateFile(writePath, winKernel.GENERIC_WRITE, 0, None,
                                 winKernel.OPEN_EXISTING, FILE_FLAG_OVERLAPPED,
                                 None)
        if writeHandle == INVALID_HANDLE_VALUE:
            if _isDebug():
                log.debug("Open write handle failed: %s" % ctypes.WinError())
            raise ctypes.WinError()
        super(Bulk, self).__init__(readHandle,
                                   onReceive,
                                   writeFileHandle=writeHandle,
                                   onReceiveSize=onReceiveSize)
Esempio n. 2
0
    def __init__(self, path, onReceive):
        """Constructor.
		@param path: The device path.
			This can be retrieved using L{hwPortUtils.listHidDevices}.
		@type path: unicode
		@param onReceive: A callable taking a received input report as its only argument.
		@type onReceive: callable(str)
		"""
        if _isDebug():
            log.debug("Opening device %s" % path)
        handle = CreateFile(path,
                            winKernel.GENERIC_READ | winKernel.GENERIC_WRITE,
                            0, None, winKernel.OPEN_EXISTING,
                            FILE_FLAG_OVERLAPPED, None)
        if handle == INVALID_HANDLE_VALUE:
            if _isDebug():
                log.debug("Open failed: %s" % ctypes.WinError())
            raise ctypes.WinError()
        pd = ctypes.c_void_p()
        if not ctypes.windll.hid.HidD_GetPreparsedData(handle, byref(pd)):
            raise ctypes.WinError()
        caps = HIDP_CAPS()
        ctypes.windll.hid.HidP_GetCaps(pd, byref(caps))
        ctypes.windll.hid.HidD_FreePreparsedData(pd)
        if _isDebug():
            log.debug("Report byte lengths: input %d, output %d, feature %d" %
                      (caps.InputReportByteLength, caps.OutputReportByteLength,
                       caps.FeatureReportByteLength))
        self._featureSize = caps.FeatureReportByteLength
        # Reading any less than caps.InputReportByteLength is an error.
        # On Windows 7, writing any less than caps.OutputReportByteLength is also an error.
        super(Hid, self).__init__(handle,
                                  onReceive,
                                  onReceiveSize=caps.InputReportByteLength,
                                  writeSize=caps.OutputReportByteLength)
Esempio n. 3
0
    def __init__(self,
                 path: str,
                 epIn: int,
                 epOut: int,
                 onReceive: Callable[[bytes], None],
                 onReceiveSize: int = 1,
                 onReadError: Optional[Callable[[int], bool]] = None):
        """Constructor.
		@param path: The device path.
		@param epIn: The endpoint to read data from.
		@param epOut: The endpoint to write data to.
		@param onReceive: A callable taking a received input report as its only argument.
		@param onReadError: An optional callable that handles read errors.
		  It takes an error code and returns True if the error has been handled,
		  allowing the read loop to exit cleanly, or False if an exception should be thrown.
		"""
        if _isDebug():
            log.debug("Opening device %s" % path)
        readPath = "{path}\\{endpoint}".format(path=path, endpoint=epIn)
        writePath = "{path}\\{endpoint}".format(path=path, endpoint=epOut)
        readHandle = CreateFile(readPath, winKernel.GENERIC_READ, 0, None,
                                winKernel.OPEN_EXISTING, FILE_FLAG_OVERLAPPED,
                                None)
        if readHandle == INVALID_HANDLE_VALUE:
            if _isDebug():
                log.debug("Open read handle failed: %s" % ctypes.WinError())
            raise ctypes.WinError()
        writeHandle = CreateFile(writePath, winKernel.GENERIC_WRITE, 0, None,
                                 winKernel.OPEN_EXISTING, FILE_FLAG_OVERLAPPED,
                                 None)
        if writeHandle == INVALID_HANDLE_VALUE:
            if _isDebug():
                log.debug("Open write handle failed: %s" % ctypes.WinError())
            raise ctypes.WinError()
        super(Bulk, self).__init__(readHandle,
                                   onReceive,
                                   writeFileHandle=writeHandle,
                                   onReceiveSize=onReceiveSize,
                                   onReadError=onReadError)
Esempio n. 4
0
def _getHidInfo(hwId, path):
    info = {"hardwareID": hwId, "devicePath": path}
    hwId = hwId.split("\\", 1)[1]
    if hwId.startswith("VID"):
        info["provider"] = "usb"
        info["usbID"] = hwId[:17]  # VID_xxxx&PID_xxxx
    elif hwId.startswith("{00001124-0000-1000-8000-00805f9b34fb}"):
        info["provider"] = "bluetooth"
    else:
        # Unknown provider.
        info["provider"] = None
        return info
    # Fetch additional info about the HID device.
    from serial.win32 import CreateFile, INVALID_HANDLE_VALUE, FILE_FLAG_OVERLAPPED
    handle = CreateFile(path, 0,
                        winKernel.FILE_SHARE_READ | winKernel.FILE_SHARE_WRITE,
                        None, winKernel.OPEN_EXISTING, FILE_FLAG_OVERLAPPED,
                        None)
    if handle == INVALID_HANDLE_VALUE:
        if _isDebug():
            log.debugWarning(
                "Opening device {dev} to get additional info failed: {exc}".
                format(dev=path, exc=ctypes.WinError()))
        return info
    try:
        attribs = HIDD_ATTRIBUTES()
        if ctypes.windll.hid.HidD_GetAttributes(handle, ctypes.byref(attribs)):
            info["vendorID"] = attribs.VendorID
            info["productID"] = attribs.ProductID
            info["versionNumber"] = attribs.VersionNumber
        else:
            if _isDebug():
                log.debugWarning("HidD_GetAttributes failed")
        buf = ctypes.create_unicode_buffer(128)
        bytes = ctypes.sizeof(buf)
        if ctypes.windll.hid.HidD_GetManufacturerString(handle, buf, bytes):
            info["manufacturer"] = buf.value
        if ctypes.windll.hid.HidD_GetProductString(handle, buf, bytes):
            info["product"] = buf.value
        pd = ctypes.c_void_p()
        if ctypes.windll.hid.HidD_GetPreparsedData(handle, ctypes.byref(pd)):
            try:
                caps = hidpi.HIDP_CAPS()
                ctypes.windll.hid.HidP_GetCaps(pd, ctypes.byref(caps))
                info['HIDUsagePage'] = caps.UsagePage
            finally:
                ctypes.windll.hid.HidD_FreePreparsedData(pd)
    finally:
        winKernel.closeHandle(handle)
    return info
Esempio n. 5
0
def _getHidInfo(hwId, path):
    info = {"hardwareID": hwId, "devicePath": path}
    hwId = hwId.split("\\", 1)[1]
    if hwId.startswith("VID"):
        info["provider"] = "usb"
        info["usbID"] = hwId[:17]  # VID_xxxx&PID_xxxx
        return info
    if not hwId.startswith(
            "{00001124-0000-1000-8000-00805f9b34fb}"):  # Not Bluetooth
        # Unknown provider.
        info["provider"] = None
        return info
    info["provider"] = "bluetooth"
    # Fetch additional info about the HID device.
    # This is a bit slow, so we only do it for Bluetooth,
    # as this info might be necessary to identify Bluetooth devices.
    from serial.win32 import CreateFile, INVALID_HANDLE_VALUE, FILE_FLAG_OVERLAPPED
    handle = CreateFile(path, 0,
                        winKernel.FILE_SHARE_READ | winKernel.FILE_SHARE_WRITE,
                        None, winKernel.OPEN_EXISTING, FILE_FLAG_OVERLAPPED,
                        None)
    if handle == INVALID_HANDLE_VALUE:
        if _isDebug():
            log.debug(
                u"Opening device {dev} to get additional info failed: {exc}".
                format(dev=path, exc=ctypes.WinError()))
        return info
    try:
        attribs = HIDD_ATTRIBUTES()
        if ctypes.windll.hid.HidD_GetAttributes(handle, ctypes.byref(attribs)):
            info["vendorID"] = attribs.VendorID
            info["productID"] = attribs.ProductID
            info["versionNumber"] = attribs.VersionNumber
        buf = ctypes.create_unicode_buffer(128)
        bytes = ctypes.sizeof(buf)
        if ctypes.windll.hid.HidD_GetManufacturerString(handle, buf, bytes):
            info["manufacturer"] = buf.value
        if ctypes.windll.hid.HidD_GetProductString(handle, buf, bytes):
            info["product"] = buf.value
    finally:
        winKernel.closeHandle(handle)
    return info
Esempio n. 6
0
    def __init__(self,
                 path: str,
                 onReceive: Callable[[bytes], None],
                 exclusive: bool = True):
        """Constructor.
		@param path: The device path.
			This can be retrieved using L{hwPortUtils.listHidDevices}.
		@param onReceive: A callable taking a received input report as its only argument.
		@param exclusive: Whether to block other application's access to this device.
		"""
        if _isDebug():
            log.debug("Opening device %s" % path)
        handle = CreateFile(
            path, winKernel.GENERIC_READ | winKernel.GENERIC_WRITE,
            0 if exclusive else winKernel.FILE_SHARE_READ
            | winKernel.FILE_SHARE_WRITE, None, winKernel.OPEN_EXISTING,
            FILE_FLAG_OVERLAPPED, None)
        if handle == INVALID_HANDLE_VALUE:
            if _isDebug():
                log.debug("Open failed: %s" % ctypes.WinError())
            raise ctypes.WinError()
        pd = ctypes.c_void_p()
        if not hidDll.HidD_GetPreparsedData(handle, byref(pd)):
            raise ctypes.WinError()
        self._pd = pd
        caps = self.caps
        self.usagePage = caps.UsagePage
        if _isDebug():
            log.debug("usage ID: 0X%X" % caps.Usage)
            log.debug("usage page: 0X%X" % caps.UsagePage)
            log.debug("Report byte lengths: input %d, output %d, feature %d" %
                      (caps.InputReportByteLength, caps.OutputReportByteLength,
                       caps.FeatureReportByteLength))
        self._featureSize = caps.FeatureReportByteLength
        self._writeSize = caps.OutputReportByteLength
        self._readSize = caps.InputReportByteLength
        # Reading any less than caps.InputReportByteLength is an error.
        super().__init__(handle,
                         onReceive,
                         onReceiveSize=caps.InputReportByteLength)