| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "device/usb/usb_device_impl.h" | 5 #include "device/usb/usb_device_impl.h" |
| 6 | 6 |
| 7 #include <fcntl.h> | 7 #include <fcntl.h> |
| 8 #include <stddef.h> | 8 #include <stddef.h> |
| 9 | 9 |
| 10 #include <algorithm> | 10 #include <algorithm> |
| 11 | 11 |
| 12 #include "base/bind.h" | 12 #include "base/bind.h" |
| 13 #include "base/location.h" | 13 #include "base/location.h" |
| 14 #include "base/posix/eintr_wrapper.h" | 14 #include "base/posix/eintr_wrapper.h" |
| 15 #include "base/sequenced_task_runner.h" | 15 #include "base/sequenced_task_runner.h" |
| 16 #include "base/single_thread_task_runner.h" | 16 #include "base/single_thread_task_runner.h" |
| 17 #include "base/stl_util.h" | 17 #include "base/stl_util.h" |
| 18 #include "base/threading/thread_task_runner_handle.h" | 18 #include "base/threading/thread_task_runner_handle.h" |
| 19 #include "build/build_config.h" | 19 #include "build/build_config.h" |
| 20 #include "components/device_event_log/device_event_log.h" | 20 #include "components/device_event_log/device_event_log.h" |
| 21 #include "device/usb/usb_context.h" | 21 #include "device/usb/usb_context.h" |
| 22 #include "device/usb/usb_descriptors.h" | 22 #include "device/usb/usb_descriptors.h" |
| 23 #include "device/usb/usb_device_handle_impl.h" | 23 #include "device/usb/usb_device_handle_impl.h" |
| 24 #include "device/usb/usb_error.h" | 24 #include "device/usb/usb_error.h" |
| 25 #include "third_party/libusb/src/libusb/libusb.h" | 25 #include "third_party/libusb/src/libusb/libusb.h" |
| 26 | 26 |
| 27 namespace device { | 27 namespace device { |
| 28 | 28 |
| 29 namespace { | |
| 30 | |
| 31 void ConvertConfigDescriptor(const libusb_config_descriptor* platform_config, | |
| 32 UsbConfigDescriptor* configuration) { | |
| 33 for (size_t i = 0; i < platform_config->bNumInterfaces; ++i) { | |
| 34 const struct libusb_interface* platform_interface = | |
| 35 &platform_config->interface[i]; | |
| 36 for (int j = 0; j < platform_interface->num_altsetting; ++j) { | |
| 37 const struct libusb_interface_descriptor* platform_alt_setting = | |
| 38 &platform_interface->altsetting[j]; | |
| 39 UsbInterfaceDescriptor interface( | |
| 40 platform_alt_setting->bInterfaceNumber, | |
| 41 platform_alt_setting->bAlternateSetting, | |
| 42 platform_alt_setting->bInterfaceClass, | |
| 43 platform_alt_setting->bInterfaceSubClass, | |
| 44 platform_alt_setting->bInterfaceProtocol); | |
| 45 | |
| 46 interface.endpoints.reserve(platform_alt_setting->bNumEndpoints); | |
| 47 for (size_t k = 0; k < platform_alt_setting->bNumEndpoints; ++k) { | |
| 48 const struct libusb_endpoint_descriptor* platform_endpoint = | |
| 49 &platform_alt_setting->endpoint[k]; | |
| 50 UsbEndpointDescriptor endpoint(platform_endpoint->bEndpointAddress, | |
| 51 platform_endpoint->bmAttributes, | |
| 52 platform_endpoint->wMaxPacketSize, | |
| 53 platform_endpoint->bInterval); | |
| 54 endpoint.extra_data.assign( | |
| 55 platform_endpoint->extra, | |
| 56 platform_endpoint->extra + platform_endpoint->extra_length); | |
| 57 | |
| 58 interface.endpoints.push_back(endpoint); | |
| 59 } | |
| 60 | |
| 61 interface.extra_data.assign( | |
| 62 platform_alt_setting->extra, | |
| 63 platform_alt_setting->extra + platform_alt_setting->extra_length); | |
| 64 | |
| 65 configuration->interfaces.push_back(interface); | |
| 66 } | |
| 67 } | |
| 68 | |
| 69 configuration->extra_data.assign( | |
| 70 platform_config->extra, | |
| 71 platform_config->extra + platform_config->extra_length); | |
| 72 | |
| 73 configuration->AssignFirstInterfaceNumbers(); | |
| 74 } | |
| 75 | |
| 76 } // namespace | |
| 77 | |
| 78 UsbDeviceImpl::UsbDeviceImpl( | 29 UsbDeviceImpl::UsbDeviceImpl( |
| 79 scoped_refptr<UsbContext> context, | 30 scoped_refptr<UsbContext> context, |
| 80 PlatformUsbDevice platform_device, | 31 PlatformUsbDevice platform_device, |
| 81 const libusb_device_descriptor& descriptor, | 32 const libusb_device_descriptor& descriptor, |
| 82 scoped_refptr<base::SequencedTaskRunner> blocking_task_runner) | 33 scoped_refptr<base::SequencedTaskRunner> blocking_task_runner) |
| 83 : UsbDevice(descriptor.bcdUSB, | 34 : UsbDevice(descriptor.bcdUSB, |
| 84 descriptor.bDeviceClass, | 35 descriptor.bDeviceClass, |
| 85 descriptor.bDeviceSubClass, | 36 descriptor.bDeviceSubClass, |
| 86 descriptor.bDeviceProtocol, | 37 descriptor.bDeviceProtocol, |
| 87 descriptor.idVendor, | 38 descriptor.idVendor, |
| (...skipping 22 matching lines...) Expand all Loading... |
| 110 | 61 |
| 111 blocking_task_runner_->PostTask( | 62 blocking_task_runner_->PostTask( |
| 112 FROM_HERE, | 63 FROM_HERE, |
| 113 base::Bind(&UsbDeviceImpl::OpenOnBlockingThread, this, callback)); | 64 base::Bind(&UsbDeviceImpl::OpenOnBlockingThread, this, callback)); |
| 114 } | 65 } |
| 115 | 66 |
| 116 void UsbDeviceImpl::ReadAllConfigurations() { | 67 void UsbDeviceImpl::ReadAllConfigurations() { |
| 117 libusb_device_descriptor device_descriptor; | 68 libusb_device_descriptor device_descriptor; |
| 118 int rv = libusb_get_device_descriptor(platform_device_, &device_descriptor); | 69 int rv = libusb_get_device_descriptor(platform_device_, &device_descriptor); |
| 119 if (rv == LIBUSB_SUCCESS) { | 70 if (rv == LIBUSB_SUCCESS) { |
| 120 uint8_t num_configurations = device_descriptor.bNumConfigurations; | 71 UsbDeviceDescriptor desc; |
| 121 configurations_.reserve(num_configurations); | 72 for (uint8_t i = 0; i < device_descriptor.bNumConfigurations; ++i) { |
| 122 for (uint8_t i = 0; i < num_configurations; ++i) { | 73 unsigned char* buffer; |
| 123 libusb_config_descriptor* platform_config; | 74 rv = libusb_get_raw_config_descriptor(platform_device_, i, &buffer); |
| 124 rv = libusb_get_config_descriptor(platform_device_, i, &platform_config); | 75 if (rv < 0) { |
| 125 if (rv != LIBUSB_SUCCESS) { | |
| 126 USB_LOG(EVENT) << "Failed to get config descriptor: " | 76 USB_LOG(EVENT) << "Failed to get config descriptor: " |
| 127 << ConvertPlatformUsbErrorToString(rv); | 77 << ConvertPlatformUsbErrorToString(rv); |
| 128 continue; | 78 continue; |
| 129 } | 79 } |
| 130 | 80 |
| 131 UsbConfigDescriptor config_descriptor( | 81 if (!desc.Parse(std::vector<uint8_t>(buffer, buffer + rv))) |
| 132 platform_config->bConfigurationValue, | 82 USB_LOG(EVENT) << "Config descriptor index " << i << " was corrupt."; |
| 133 (platform_config->bmAttributes & 0x40) != 0, | 83 free(buffer); |
| 134 (platform_config->bmAttributes & 0x20) != 0, | |
| 135 platform_config->MaxPower * 2); | |
| 136 ConvertConfigDescriptor(platform_config, &config_descriptor); | |
| 137 configurations_.push_back(config_descriptor); | |
| 138 libusb_free_config_descriptor(platform_config); | |
| 139 } | 84 } |
| 85 configurations_.swap(desc.configurations); |
| 140 } else { | 86 } else { |
| 141 USB_LOG(EVENT) << "Failed to get device descriptor: " | 87 USB_LOG(EVENT) << "Failed to get device descriptor: " |
| 142 << ConvertPlatformUsbErrorToString(rv); | 88 << ConvertPlatformUsbErrorToString(rv); |
| 143 } | 89 } |
| 144 } | 90 } |
| 145 | 91 |
| 146 void UsbDeviceImpl::RefreshActiveConfiguration() { | 92 void UsbDeviceImpl::RefreshActiveConfiguration() { |
| 147 libusb_config_descriptor* platform_config; | 93 uint8_t config_value; |
| 148 int rv = | 94 int rv = libusb_get_active_config_value(platform_device_, &config_value); |
| 149 libusb_get_active_config_descriptor(platform_device_, &platform_config); | |
| 150 if (rv != LIBUSB_SUCCESS) { | 95 if (rv != LIBUSB_SUCCESS) { |
| 151 USB_LOG(EVENT) << "Failed to get config descriptor: " | 96 USB_LOG(EVENT) << "Failed to get active configuration: " |
| 152 << ConvertPlatformUsbErrorToString(rv); | 97 << ConvertPlatformUsbErrorToString(rv); |
| 153 return; | 98 return; |
| 154 } | 99 } |
| 155 | 100 |
| 156 ActiveConfigurationChanged(platform_config->bConfigurationValue); | 101 ActiveConfigurationChanged(config_value); |
| 157 libusb_free_config_descriptor(platform_config); | |
| 158 } | 102 } |
| 159 | 103 |
| 160 void UsbDeviceImpl::OpenOnBlockingThread(const OpenCallback& callback) { | 104 void UsbDeviceImpl::OpenOnBlockingThread(const OpenCallback& callback) { |
| 161 PlatformUsbDeviceHandle handle; | 105 PlatformUsbDeviceHandle handle; |
| 162 const int rv = libusb_open(platform_device_, &handle); | 106 const int rv = libusb_open(platform_device_, &handle); |
| 163 if (LIBUSB_SUCCESS == rv) { | 107 if (LIBUSB_SUCCESS == rv) { |
| 164 task_runner_->PostTask( | 108 task_runner_->PostTask( |
| 165 FROM_HERE, base::Bind(&UsbDeviceImpl::Opened, this, handle, callback)); | 109 FROM_HERE, base::Bind(&UsbDeviceImpl::Opened, this, handle, callback)); |
| 166 } else { | 110 } else { |
| 167 USB_LOG(EVENT) << "Failed to open device: " | 111 USB_LOG(EVENT) << "Failed to open device: " |
| 168 << ConvertPlatformUsbErrorToString(rv); | 112 << ConvertPlatformUsbErrorToString(rv); |
| 169 task_runner_->PostTask(FROM_HERE, base::Bind(callback, nullptr)); | 113 task_runner_->PostTask(FROM_HERE, base::Bind(callback, nullptr)); |
| 170 } | 114 } |
| 171 } | 115 } |
| 172 | 116 |
| 173 void UsbDeviceImpl::Opened(PlatformUsbDeviceHandle platform_handle, | 117 void UsbDeviceImpl::Opened(PlatformUsbDeviceHandle platform_handle, |
| 174 const OpenCallback& callback) { | 118 const OpenCallback& callback) { |
| 175 DCHECK(thread_checker_.CalledOnValidThread()); | 119 DCHECK(thread_checker_.CalledOnValidThread()); |
| 176 scoped_refptr<UsbDeviceHandle> device_handle = new UsbDeviceHandleImpl( | 120 scoped_refptr<UsbDeviceHandle> device_handle = new UsbDeviceHandleImpl( |
| 177 context_, this, platform_handle, blocking_task_runner_); | 121 context_, this, platform_handle, blocking_task_runner_); |
| 178 handles().push_back(device_handle.get()); | 122 handles().push_back(device_handle.get()); |
| 179 callback.Run(device_handle); | 123 callback.Run(device_handle); |
| 180 } | 124 } |
| 181 | 125 |
| 182 } // namespace device | 126 } // namespace device |
| OLD | NEW |