Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(19)

Side by Side Diff: device/devices_app/usb/device_impl_unittest.cc

Issue 1618393004: Update device/usb and its Mojo interface for variable size ISO packets. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 4 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2015 The Chromium Authors. All rights reserved. 1 // Copyright 2015 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/devices_app/usb/device_impl.h" 5 #include "device/devices_app/usb/device_impl.h"
6 6
7 #include <stddef.h> 7 #include <stddef.h>
8 #include <stdint.h> 8 #include <stdint.h>
9
9 #include <map> 10 #include <map>
11 #include <numeric>
10 #include <queue> 12 #include <queue>
11 #include <set> 13 #include <set>
14 #include <string>
12 #include <utility> 15 #include <utility>
13 #include <vector> 16 #include <vector>
14 17
15 #include "base/bind.h" 18 #include "base/bind.h"
16 #include "base/macros.h" 19 #include "base/macros.h"
17 #include "base/message_loop/message_loop.h" 20 #include "base/message_loop/message_loop.h"
18 #include "base/run_loop.h" 21 #include "base/run_loop.h"
19 #include "base/stl_util.h" 22 #include "base/stl_util.h"
20 #include "device/devices_app/usb/fake_permission_provider.h" 23 #include "device/devices_app/usb/fake_permission_provider.h"
21 #include "device/usb/mock_usb_device.h" 24 #include "device/usb/mock_usb_device.h"
22 #include "device/usb/mock_usb_device_handle.h" 25 #include "device/usb/mock_usb_device_handle.h"
23 #include "mojo/public/cpp/bindings/interface_request.h" 26 #include "mojo/public/cpp/bindings/interface_request.h"
24 #include "testing/gtest/include/gtest/gtest.h" 27 #include "testing/gtest/include/gtest/gtest.h"
25 28
26 using ::testing::Invoke; 29 using ::testing::Invoke;
27 using ::testing::_; 30 using ::testing::_;
28 31
29 namespace device { 32 namespace device {
30 namespace usb { 33 namespace usb {
31 34
32 namespace { 35 namespace {
33 36
34 class ConfigBuilder { 37 class ConfigBuilder {
35 public: 38 public:
36 ConfigBuilder(uint8_t value) { config_.configuration_value = value; } 39 explicit ConfigBuilder(uint8_t value) { config_.configuration_value = value; }
37 40
38 ConfigBuilder& AddInterface(uint8_t interface_number, 41 ConfigBuilder& AddInterface(uint8_t interface_number,
39 uint8_t alternate_setting, 42 uint8_t alternate_setting,
40 uint8_t class_code, 43 uint8_t class_code,
41 uint8_t subclass_code, 44 uint8_t subclass_code,
42 uint8_t protocol_code) { 45 uint8_t protocol_code) {
43 UsbInterfaceDescriptor interface; 46 UsbInterfaceDescriptor interface;
44 interface.interface_number = interface_number; 47 interface.interface_number = interface_number;
45 interface.alternate_setting = alternate_setting; 48 interface.alternate_setting = alternate_setting;
46 interface.interface_class = class_code; 49 interface.interface_class = class_code;
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after
94 mojo::Array<uint8_t> actual_bytes) { 97 mojo::Array<uint8_t> actual_bytes) {
95 EXPECT_EQ(expected_status, actual_status); 98 EXPECT_EQ(expected_status, actual_status);
96 ASSERT_EQ(expected_bytes.size(), actual_bytes.size()); 99 ASSERT_EQ(expected_bytes.size(), actual_bytes.size());
97 for (size_t i = 0; i < actual_bytes.size(); ++i) { 100 for (size_t i = 0; i < actual_bytes.size(); ++i) {
98 EXPECT_EQ(expected_bytes[i], actual_bytes[i]) 101 EXPECT_EQ(expected_bytes[i], actual_bytes[i])
99 << "Contents differ at index: " << i; 102 << "Contents differ at index: " << i;
100 } 103 }
101 continuation.Run(); 104 continuation.Run();
102 } 105 }
103 106
104 void ExpectPacketsAndThen( 107 void ExpectPacketsOutAndThen(const std::vector<uint32_t>& expected_packets,
105 TransferStatus expected_status, 108 const base::Closure& continuation,
106 const std::vector<std::vector<uint8_t>>& expected_packets, 109 mojo::Array<IsochronousPacketPtr> actual_packets) {
107 const base::Closure& continuation,
108 TransferStatus actual_status,
109 mojo::Array<mojo::Array<uint8_t>> actual_packets) {
110 EXPECT_EQ(expected_status, actual_status);
111 ASSERT_EQ(expected_packets.size(), actual_packets.size()); 110 ASSERT_EQ(expected_packets.size(), actual_packets.size());
112 for (size_t i = 0; i < expected_packets.size(); ++i) { 111 for (size_t i = 0; i < expected_packets.size(); ++i) {
113 EXPECT_EQ(expected_packets[i].size(), actual_packets[i].size()) 112 EXPECT_EQ(expected_packets[i], actual_packets[i]->transferred_length)
114 << "Packet sizes differ at index: " << i; 113 << "Packet lengths differ at index: " << i;
115 for (size_t j = 0; j < expected_packets[i].size(); ++j) { 114 EXPECT_EQ(TransferStatus::COMPLETED, actual_packets[i]->status)
116 EXPECT_EQ(expected_packets[i][j], actual_packets[i][j]) 115 << "Packet at index " << i << " not completed.";
117 << "Contents of packet " << i << " differ at index " << j;
118 }
119 } 116 }
120 continuation.Run(); 117 continuation.Run();
121 } 118 }
119
120 void ExpectPacketsInAndThen(const std::vector<uint8_t>& expected_bytes,
121 const std::vector<uint32_t>& expected_packets,
122 const base::Closure& continuation,
123 mojo::Array<uint8_t> actual_bytes,
124 mojo::Array<IsochronousPacketPtr> actual_packets) {
125 ASSERT_EQ(expected_packets.size(), actual_packets.size());
126 for (size_t i = 0; i < expected_packets.size(); ++i) {
127 EXPECT_EQ(expected_packets[i], actual_packets[i]->transferred_length)
128 << "Packet lengths differ at index: " << i;
129 EXPECT_EQ(TransferStatus::COMPLETED, actual_packets[i]->status)
130 << "Packet at index " << i << " not completed.";
131 }
132 ASSERT_EQ(expected_bytes.size(), actual_bytes.size());
133 for (size_t i = 0; i < expected_bytes.size(); ++i) {
134 EXPECT_EQ(expected_bytes[i], actual_bytes[i])
135 << "Contents differ at index: " << i;
136 }
137 continuation.Run();
138 }
122 139
123 void ExpectTransferStatusAndThen(TransferStatus expected_status, 140 void ExpectTransferStatusAndThen(TransferStatus expected_status,
124 const base::Closure& continuation, 141 const base::Closure& continuation,
125 TransferStatus actual_status) { 142 TransferStatus actual_status) {
126 EXPECT_EQ(expected_status, actual_status); 143 EXPECT_EQ(expected_status, actual_status);
127 continuation.Run(); 144 continuation.Run();
128 } 145 }
129 146
130 class USBDeviceImplTest : public testing::Test { 147 class USBDeviceImplTest : public testing::Test {
131 public: 148 public:
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after
178 .WillByDefault(Invoke(this, &USBDeviceImplTest::ReleaseInterface)); 195 .WillByDefault(Invoke(this, &USBDeviceImplTest::ReleaseInterface));
179 ON_CALL(mock_handle(), SetInterfaceAlternateSetting(_, _, _)) 196 ON_CALL(mock_handle(), SetInterfaceAlternateSetting(_, _, _))
180 .WillByDefault( 197 .WillByDefault(
181 Invoke(this, &USBDeviceImplTest::SetInterfaceAlternateSetting)); 198 Invoke(this, &USBDeviceImplTest::SetInterfaceAlternateSetting));
182 ON_CALL(mock_handle(), ResetDevice(_)) 199 ON_CALL(mock_handle(), ResetDevice(_))
183 .WillByDefault(Invoke(this, &USBDeviceImplTest::ResetDevice)); 200 .WillByDefault(Invoke(this, &USBDeviceImplTest::ResetDevice));
184 ON_CALL(mock_handle(), ControlTransfer(_, _, _, _, _, _, _, _, _, _)) 201 ON_CALL(mock_handle(), ControlTransfer(_, _, _, _, _, _, _, _, _, _))
185 .WillByDefault(Invoke(this, &USBDeviceImplTest::ControlTransfer)); 202 .WillByDefault(Invoke(this, &USBDeviceImplTest::ControlTransfer));
186 ON_CALL(mock_handle(), GenericTransfer(_, _, _, _, _, _)) 203 ON_CALL(mock_handle(), GenericTransfer(_, _, _, _, _, _))
187 .WillByDefault(Invoke(this, &USBDeviceImplTest::GenericTransfer)); 204 .WillByDefault(Invoke(this, &USBDeviceImplTest::GenericTransfer));
188 ON_CALL(mock_handle(), IsochronousTransfer(_, _, _, _, _, _, _, _)) 205 ON_CALL(mock_handle(), IsochronousTransferIn(_, _, _, _))
189 .WillByDefault(Invoke(this, &USBDeviceImplTest::IsochronousTransfer)); 206 .WillByDefault(Invoke(this, &USBDeviceImplTest::IsochronousTransferIn));
207 ON_CALL(mock_handle(), IsochronousTransferOut(_, _, _, _, _))
208 .WillByDefault(
209 Invoke(this, &USBDeviceImplTest::IsochronousTransferOut));
190 210
191 return proxy; 211 return proxy;
192 } 212 }
193 213
194 DevicePtr GetMockDeviceProxy() { 214 DevicePtr GetMockDeviceProxy() {
195 return GetMockDeviceProxy(0x1234, 0x5678, "ACME", "Frobinator", "ABCDEF"); 215 return GetMockDeviceProxy(0x1234, 0x5678, "ACME", "Frobinator", "ABCDEF");
196 } 216 }
197 217
198 void AddMockConfig(const ConfigBuilder& builder) { 218 void AddMockConfig(const ConfigBuilder& builder) {
199 const UsbConfigDescriptor& config = builder.config(); 219 const UsbConfigDescriptor& config = builder.config();
200 DCHECK(!ContainsKey(mock_configs_, config.configuration_value)); 220 DCHECK(!ContainsKey(mock_configs_, config.configuration_value));
201 mock_configs_[config.configuration_value] = config; 221 mock_configs_[config.configuration_value] = config;
202 } 222 }
203 223
204 void AddMockInboundData(const std::vector<uint8_t>& data) { 224 void AddMockInboundData(const std::vector<uint8_t>& data) {
205 mock_inbound_data_.push(data); 225 mock_inbound_data_.push(data);
206 } 226 }
207 227
228 void AddMockInboundPackets(
229 const std::vector<uint8_t>& data,
230 const std::vector<UsbDeviceHandle::IsochronousPacket>& packets) {
231 mock_inbound_data_.push(data);
232 mock_inbound_packets_.push(packets);
233 }
234
208 void AddMockOutboundData(const std::vector<uint8_t>& data) { 235 void AddMockOutboundData(const std::vector<uint8_t>& data) {
209 mock_outbound_data_.push(data); 236 mock_outbound_data_.push(data);
210 } 237 }
211 238
239 void AddMockOutboundPackets(
240 const std::vector<uint8_t>& data,
241 const std::vector<UsbDeviceHandle::IsochronousPacket>& packets) {
242 mock_outbound_data_.push(data);
243 mock_outbound_packets_.push(packets);
244 }
245
212 private: 246 private:
213 void OpenMockHandle(const UsbDevice::OpenCallback& callback) { 247 void OpenMockHandle(const UsbDevice::OpenCallback& callback) {
214 EXPECT_FALSE(is_device_open_); 248 EXPECT_FALSE(is_device_open_);
215 is_device_open_ = true; 249 is_device_open_ = true;
216 callback.Run(mock_handle_); 250 callback.Run(mock_handle_);
217 } 251 }
218 252
219 void CloseMockHandle() { 253 void CloseMockHandle() {
220 EXPECT_TRUE(is_device_open_); 254 EXPECT_TRUE(is_device_open_);
221 is_device_open_ = false; 255 is_device_open_ = false;
(...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after
328 scoped_refptr<net::IOBuffer> buffer, 362 scoped_refptr<net::IOBuffer> buffer,
329 size_t length, 363 size_t length,
330 unsigned int timeout, 364 unsigned int timeout,
331 const UsbDeviceHandle::TransferCallback& callback) { 365 const UsbDeviceHandle::TransferCallback& callback) {
332 if (direction == USB_DIRECTION_INBOUND) 366 if (direction == USB_DIRECTION_INBOUND)
333 InboundTransfer(callback); 367 InboundTransfer(callback);
334 else 368 else
335 OutboundTransfer(buffer, length, callback); 369 OutboundTransfer(buffer, length, callback);
336 } 370 }
337 371
338 void IsochronousTransfer(UsbEndpointDirection direction, 372 void IsochronousTransferIn(
339 uint8_t endpoint, 373 uint8_t endpoint_number,
340 scoped_refptr<net::IOBuffer> buffer, 374 const std::vector<uint32_t>& packet_lengths,
341 size_t length, 375 unsigned int timeout,
342 unsigned int packets, 376 const UsbDeviceHandle::IsochronousTransferCallback& callback) {
343 unsigned int packet_length, 377 ASSERT_FALSE(mock_inbound_data_.empty());
344 unsigned int timeout, 378 const std::vector<uint8_t>& bytes = mock_inbound_data_.front();
345 const UsbDeviceHandle::TransferCallback& callback) { 379 size_t length = bytes.size();
346 if (direction == USB_DIRECTION_INBOUND) 380 scoped_refptr<net::IOBuffer> buffer = new net::IOBuffer(length);
347 InboundTransfer(callback); 381 std::copy(bytes.begin(), bytes.end(), buffer->data());
348 else 382 mock_inbound_data_.pop();
349 OutboundTransfer(buffer, length, callback); 383
384 ASSERT_FALSE(mock_inbound_packets_.empty());
385 std::vector<UsbDeviceHandle::IsochronousPacket> packets =
386 mock_inbound_packets_.front();
387 ASSERT_EQ(packets.size(), packet_lengths.size());
388 for (size_t i = 0; i < packets.size(); ++i) {
389 EXPECT_EQ(packets[i].length, packet_lengths[i])
390 << "Packet lengths differ at index: " << i;
391 }
392 mock_inbound_packets_.pop();
393
394 callback.Run(buffer, packets);
395 }
396
397 void IsochronousTransferOut(
398 uint8_t endpoint_number,
399 scoped_refptr<net::IOBuffer> buffer,
400 const std::vector<uint32_t>& packet_lengths,
401 unsigned int timeout,
402 const UsbDeviceHandle::IsochronousTransferCallback& callback) {
403 ASSERT_FALSE(mock_outbound_data_.empty());
404 const std::vector<uint8_t>& bytes = mock_outbound_data_.front();
405 size_t length =
406 std::accumulate(packet_lengths.begin(), packet_lengths.end(), 0u);
407 ASSERT_EQ(bytes.size(), length);
408 for (size_t i = 0; i < length; ++i) {
409 EXPECT_EQ(bytes[i], buffer->data()[i]) << "Contents differ at index: "
410 << i;
411 }
412 mock_outbound_data_.pop();
413
414 ASSERT_FALSE(mock_outbound_packets_.empty());
415 std::vector<UsbDeviceHandle::IsochronousPacket> packets =
416 mock_outbound_packets_.front();
417 ASSERT_EQ(packets.size(), packet_lengths.size());
418 for (size_t i = 0; i < packets.size(); ++i) {
419 EXPECT_EQ(packets[i].length, packet_lengths[i])
420 << "Packet lengths differ at index: " << i;
421 }
422 mock_outbound_packets_.pop();
423
424 callback.Run(buffer, packets);
350 } 425 }
351 426
352 scoped_ptr<base::MessageLoop> message_loop_; 427 scoped_ptr<base::MessageLoop> message_loop_;
353 scoped_refptr<MockUsbDevice> mock_device_; 428 scoped_refptr<MockUsbDevice> mock_device_;
354 scoped_refptr<MockUsbDeviceHandle> mock_handle_; 429 scoped_refptr<MockUsbDeviceHandle> mock_handle_;
355 bool is_device_open_; 430 bool is_device_open_;
356 bool allow_reset_; 431 bool allow_reset_;
357 432
358 std::map<uint8_t, UsbConfigDescriptor> mock_configs_; 433 std::map<uint8_t, UsbConfigDescriptor> mock_configs_;
359 uint8_t current_config_; 434 uint8_t current_config_;
360 435
361 std::queue<std::vector<uint8_t>> mock_inbound_data_; 436 std::queue<std::vector<uint8_t>> mock_inbound_data_;
362 std::queue<std::vector<uint8_t>> mock_outbound_data_; 437 std::queue<std::vector<uint8_t>> mock_outbound_data_;
438 std::queue<std::vector<UsbDeviceHandle::IsochronousPacket>>
439 mock_inbound_packets_;
440 std::queue<std::vector<UsbDeviceHandle::IsochronousPacket>>
441 mock_outbound_packets_;
363 442
364 std::set<uint8_t> claimed_interfaces_; 443 std::set<uint8_t> claimed_interfaces_;
365 444
366 FakePermissionProvider permission_provider_; 445 FakePermissionProvider permission_provider_;
367 446
368 DISALLOW_COPY_AND_ASSIGN(USBDeviceImplTest); 447 DISALLOW_COPY_AND_ASSIGN(USBDeviceImplTest);
369 }; 448 };
370 449
371 } // namespace 450 } // namespace
372 451
(...skipping 377 matching lines...) Expand 10 before | Expand all | Expand 10 after
750 829
751 EXPECT_CALL(mock_device(), Open(_)); 830 EXPECT_CALL(mock_device(), Open(_));
752 831
753 { 832 {
754 base::RunLoop loop; 833 base::RunLoop loop;
755 device->Open(base::Bind(&ExpectOpenAndThen, OpenDeviceError::OK, 834 device->Open(base::Bind(&ExpectOpenAndThen, OpenDeviceError::OK,
756 loop.QuitClosure())); 835 loop.QuitClosure()));
757 loop.Run(); 836 loop.Run();
758 } 837 }
759 838
760 std::string outbound_packet_data = "aaaaaaaabbbbbbbbccccccccdddddddd"; 839 std::vector<UsbDeviceHandle::IsochronousPacket> fake_packets(4);
761 std::vector<uint8_t> fake_outbound_packets(outbound_packet_data.size()); 840 for (size_t i = 0; i < fake_packets.size(); ++i) {
762 std::copy(outbound_packet_data.begin(), outbound_packet_data.end(), 841 fake_packets[i].length = 8;
763 fake_outbound_packets.begin()); 842 fake_packets[i].transferred_length = 8;
843 fake_packets[i].status = USB_TRANSFER_COMPLETED;
844 }
845 std::vector<uint32_t> fake_packet_lengths(4, 8);
764 846
765 std::string inbound_packet_data = "ddddddddccccccccbbbbbbbbaaaaaaaa"; 847 std::vector<uint32_t> expected_transferred_lengths(4, 8);
766 std::vector<uint8_t> fake_inbound_packets(inbound_packet_data.size()); 848
767 std::copy(inbound_packet_data.begin(), inbound_packet_data.end(), 849 std::string outbound_data = "aaaaaaaabbbbbbbbccccccccdddddddd";
768 fake_inbound_packets.begin()); 850 std::vector<uint8_t> fake_outbound_data(outbound_data.size());
851 std::copy(outbound_data.begin(), outbound_data.end(),
852 fake_outbound_data.begin());
853
854 std::string inbound_data = "ddddddddccccccccbbbbbbbbaaaaaaaa";
855 std::vector<uint8_t> fake_inbound_data(inbound_data.size());
856 std::copy(inbound_data.begin(), inbound_data.end(),
857 fake_inbound_data.begin());
769 858
770 AddMockConfig(ConfigBuilder(1).AddInterface(7, 0, 1, 2, 3)); 859 AddMockConfig(ConfigBuilder(1).AddInterface(7, 0, 1, 2, 3));
771 AddMockOutboundData(fake_outbound_packets); 860 AddMockOutboundPackets(fake_outbound_data, fake_packets);
772 AddMockInboundData(fake_inbound_packets); 861 AddMockInboundPackets(fake_inbound_data, fake_packets);
773 862
774 EXPECT_CALL(mock_handle(), 863 EXPECT_CALL(mock_handle(),
775 IsochronousTransfer(USB_DIRECTION_OUTBOUND, 0x01, _, 864 IsochronousTransferOut(0x01, _, fake_packet_lengths, 0, _));
776 fake_outbound_packets.size(), 4, 8, 0, _));
777 865
778 { 866 {
779 base::RunLoop loop; 867 base::RunLoop loop;
780 mojo::Array<mojo::Array<uint8_t>> packets =
781 mojo::Array<mojo::Array<uint8_t>>::New(4);
782 for (size_t i = 0; i < 4; ++i) {
783 std::vector<uint8_t> bytes(8);
784 std::copy(outbound_packet_data.begin() + i * 8,
785 outbound_packet_data.begin() + i * 8 + 8, bytes.begin());
786 packets[i].Swap(&bytes);
787 }
788 device->IsochronousTransferOut( 868 device->IsochronousTransferOut(
789 1, std::move(packets), 0, 869 1, mojo::Array<uint8_t>::From(fake_outbound_data),
790 base::Bind(&ExpectTransferStatusAndThen, TransferStatus::COMPLETED, 870 mojo::Array<uint32_t>::From(fake_packet_lengths), 0,
871 base::Bind(&ExpectPacketsOutAndThen, expected_transferred_lengths,
791 loop.QuitClosure())); 872 loop.QuitClosure()));
792 loop.Run(); 873 loop.Run();
793 } 874 }
794 875
795 EXPECT_CALL(mock_handle(), 876 EXPECT_CALL(mock_handle(),
796 IsochronousTransfer(USB_DIRECTION_INBOUND, 0x81, _, 877 IsochronousTransferIn(0x81, fake_packet_lengths, 0, _));
797 fake_inbound_packets.size(), 4, 8, 0, _));
798 878
799 { 879 {
800 base::RunLoop loop; 880 base::RunLoop loop;
801 std::vector<std::vector<uint8_t>> packets(4);
802 for (size_t i = 0; i < 4; ++i) {
803 packets[i].resize(8);
804 std::copy(inbound_packet_data.begin() + i * 8,
805 inbound_packet_data.begin() + i * 8 + 8, packets[i].begin());
806 }
807 device->IsochronousTransferIn( 881 device->IsochronousTransferIn(
808 1, 4, 8, 0, base::Bind(&ExpectPacketsAndThen, TransferStatus::COMPLETED, 882 1, mojo::Array<uint32_t>::From(fake_packet_lengths), 0,
809 packets, loop.QuitClosure())); 883 base::Bind(&ExpectPacketsInAndThen, fake_inbound_data,
884 expected_transferred_lengths, loop.QuitClosure()));
810 loop.Run(); 885 loop.Run();
811 } 886 }
812 887
813 EXPECT_CALL(mock_handle(), Close()); 888 EXPECT_CALL(mock_handle(), Close());
814 } 889 }
815 890
816 } // namespace usb 891 } // namespace usb
817 } // namespace device 892 } // namespace device
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698