Beispiel #1
0
    def __init__(self, device, setting, name=None, default_timeout_ms=None):
        """Initialize a local libusb-based USB Handle.

    Arguments:
      device: libusb device to connect to.
      setting: libusb setting with the endpoints to use for data reads/writes.
      name: Name for the device, used for log messages only.
      default_timeout_ms: Default timeout, in milliseconds, for reads/writes.

    Raises:
      InvalidEndpointsError: If the setting provided does not have exactly one
        in endpoint and one out endpoint.  Currently, this is the only type of
        interface supported.
      IOError: If the device has been disconnected.
    """
        super(LibUsbHandle,
              self).__init__(device.getSerialNumber(),
                             name=name,
                             default_timeout_ms=default_timeout_ms)
        self._setting = setting
        self._device = device

        self._read_endpoint = None
        self._write_endpoint = None
        self._handle = None

        for endpoint in self._setting.iterEndpoints():
            address = endpoint.getAddress()
            if address & libusb1.USB_ENDPOINT_DIR_MASK == libusb1.LIBUSB_ENDPOINT_IN:
                if self._read_endpoint is not None:
                    raise usb_exceptions.InvalidEndpointsError(
                        'Multiple in endpoints found')
                self._read_endpoint = address
            else:
                if self._write_endpoint is not None:
                    raise usb_exceptions.InvalidEndpointsError(
                        'Multiple out endpoints found')
                self._write_endpoint = address

        if self._read_endpoint is None:
            raise usb_exceptions.InvalidEndpointsError('Missing in endpoint')
        if self._write_endpoint is None:
            raise usb_exceptions.InvalidEndpointsError('Missing out endpoint')

        handle = self._device.open()
        iface_number = self._setting.getNumber()
        try:
            if handle.kernelDriverActive(iface_number):
                handle.detachKernelDriver(iface_number)
        except libusb1.USBError as exception:
            if exception.value == libusb1.LIBUSB_ERROR_NOT_FOUND:
                _LOG.warning('Kernel driver not found for interface: %s.',
                             iface_number)
            else:
                raise usb_exceptions.LibusbWrappingError(
                    exception, '%s failed to detach kernel driver', self)
        # Try to claim the interface, if the device is gone, raise an IOError
        try:
            handle.claimInterface(iface_number)
        except libusb1.USBError as exception:
            raise usb_exceptions.LibusbWrappingError(
                exception, '%s failed to claim interface: %d', self,
                iface_number)

        self._handle = handle
        self._interface_number = iface_number
Beispiel #2
0
    def iter_open(cls,
                  name=None,
                  interface_class=None,
                  interface_subclass=None,
                  interface_protocol=None,
                  serial_number=None,
                  port_path=None,
                  default_timeout_ms=None):
        """Find and yield locally connected devices that match.

    Note that devices are opened (and interfaces claimd) as they are yielded.
    Any devices yielded must be Close()'d.

    Args:
      name: Name to give *all* returned handles, used for logging only.
      interface_class: USB interface_class to match.
      interface_subclass: USB interface_subclass to match.
      interface_protocol: USB interface_protocol to match.
      serial_number: USB serial_number to match.
      port_path: USB Port path to match, like X-X.X.X
      default_timeout_ms: Default timeout in milliseconds of reads/writes on
        the handles yielded.

    Yields:
      UsbHandle instances that match any non-None args given.

    Raises:
      LibusbWrappingError: When a libusb call errors during open.
    """
        ctx = usb1.USBContext()
        try:
            devices = ctx.getDeviceList(skip_on_error=True)
        except libusb1.USBError as exception:
            raise usb_exceptions.LibusbWrappingError(
                exception, 'Open(name=%s, class=%s, subclass=%s, protocol=%s, '
                'serial=%s, port=%s) failed', name, interface_class,
                interface_subclass, interface_protocol, serial_number,
                port_path)

        for device in devices:
            try:
                if (serial_number is not None
                        and device.getSerialNumber() != serial_number):
                    continue

                if (port_path is not None
                        and cls._device_to_sysfs_path(device) != port_path):
                    continue

                for setting in device.iterSettings():
                    if (interface_class is not None
                            and setting.getClass() != interface_class):
                        continue
                    if (interface_subclass is not None
                            and setting.getSubClass() != interface_subclass):
                        continue
                    if (interface_protocol is not None
                            and setting.getProtocol() != interface_protocol):
                        continue

                    yield cls(device,
                              setting,
                              name=name,
                              default_timeout_ms=default_timeout_ms)
            except libusb1.USBError as exception:
                if (exception.value != libusb1.libusb_error.
                        forward_dict['LIBUSB_ERROR_ACCESS']):
                    raise