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
3// found in the LICENSE file.
4
5#include "extensions/browser/api/usb_private/usb_private_api.h"
6
7#include <string>
8#include <vector>
9
10#include "base/memory/ref_counted.h"
11#include "base/strings/utf_string_conversions.h"
12#include "device/core/device_client.h"
13#include "device/usb/usb_device_filter.h"
14#include "device/usb/usb_device_handle.h"
15#include "device/usb/usb_ids.h"
16#include "device/usb/usb_service.h"
17#include "extensions/common/api/usb_private.h"
18
19namespace usb = extensions::core_api::usb;
20namespace usb_private = extensions::core_api::usb_private;
21namespace GetDevices = usb_private::GetDevices;
22namespace GetDeviceInfo = usb_private::GetDeviceInfo;
23
24using content::BrowserThread;
25using device::UsbDevice;
26using device::UsbDeviceFilter;
27using device::UsbDeviceHandle;
28using device::UsbService;
29
30typedef std::vector<scoped_refptr<UsbDevice> > DeviceVector;
31
32namespace {
33
34const char kErrorInitService[] = "Failed to initialize USB service.";
35const char kErrorNoDevice[] = "No such device.";
36
37}  // namespace
38
39namespace extensions {
40
41UsbPrivateGetDevicesFunction::UsbPrivateGetDevicesFunction() {
42}
43
44UsbPrivateGetDevicesFunction::~UsbPrivateGetDevicesFunction() {
45}
46
47bool UsbPrivateGetDevicesFunction::Prepare() {
48  parameters_ = GetDevices::Params::Create(*args_);
49  EXTENSION_FUNCTION_VALIDATE(parameters_.get());
50  return true;
51}
52
53void UsbPrivateGetDevicesFunction::AsyncWorkStart() {
54  UsbService* service = device::DeviceClient::Get()->GetUsbService();
55  if (!service) {
56    CompleteWithError(kErrorInitService);
57    return;
58  }
59
60  std::vector<UsbDeviceFilter> filters;
61  filters.resize(parameters_->filters.size());
62  for (size_t i = 0; i < parameters_->filters.size(); ++i) {
63    CreateDeviceFilter(*parameters_->filters[i].get(), &filters[i]);
64  }
65
66  DeviceVector devices;
67  service->GetDevices(&devices);
68
69  scoped_ptr<base::ListValue> result(new base::ListValue());
70  for (DeviceVector::iterator it = devices.begin(); it != devices.end(); ++it) {
71    scoped_refptr<UsbDevice> device = *it;
72    if (filters.empty() || UsbDeviceFilter::MatchesAny(device, filters)) {
73      result->Append(new base::FundamentalValue((int)device->unique_id()));
74    }
75  }
76
77  SetResult(result.release());
78  AsyncWorkCompleted();
79}
80
81UsbPrivateGetDeviceInfoFunction::UsbPrivateGetDeviceInfoFunction() {
82}
83
84UsbPrivateGetDeviceInfoFunction::~UsbPrivateGetDeviceInfoFunction() {
85}
86
87bool UsbPrivateGetDeviceInfoFunction::Prepare() {
88  parameters_ = GetDeviceInfo::Params::Create(*args_);
89  EXTENSION_FUNCTION_VALIDATE(parameters_.get());
90  return true;
91}
92
93void UsbPrivateGetDeviceInfoFunction::AsyncWorkStart() {
94  UsbService* service = device::DeviceClient::Get()->GetUsbService();
95  if (!service) {
96    CompleteWithError(kErrorInitService);
97    return;
98  }
99
100  scoped_refptr<UsbDevice> device =
101      service->GetDeviceById(parameters_->device_id);
102  if (!device.get()) {
103    CompleteWithError(kErrorNoDevice);
104    return;
105  }
106
107  usb_private::DeviceInfo device_info;
108  device_info.vendor_id = device->vendor_id();
109  device_info.product_id = device->product_id();
110
111  const char* name = device::UsbIds::GetVendorName(device_info.vendor_id);
112  if (name) {
113    device_info.vendor_name.reset(new std::string(name));
114  }
115
116  name = device::UsbIds::GetProductName(device_info.vendor_id,
117                                        device_info.product_id);
118  if (name) {
119    device_info.product_name.reset(new std::string(name));
120  }
121
122  base::string16 utf16;
123  if (device->GetManufacturer(&utf16)) {
124    device_info.manufacturer_string.reset(
125        new std::string(base::UTF16ToUTF8(utf16)));
126  }
127
128  if (device->GetProduct(&utf16)) {
129    device_info.product_string.reset(new std::string(base::UTF16ToUTF8(utf16)));
130  }
131
132  if (device->GetSerialNumber(&utf16)) {
133    device_info.serial_string.reset(new std::string(base::UTF16ToUTF8(utf16)));
134  }
135
136  SetResult(device_info.ToValue().release());
137  AsyncWorkCompleted();
138}
139
140}  // namespace extensions
141