2 // META: script=/webusb/resources/fake-devices.js
3 // META: script=/webusb/resources/usb-helpers.js
6 function assertRejectsWithNotFoundError(promise) {
7 return assertRejectsWithError(promise, 'NotFoundError');
10 function assertRejectsWithTypeError(promise) {
11 return assertRejectsWithError(promise, 'TypeError');
14 function assertRejectsWithNotOpenError(promise) {
15 return assertRejectsWithError(
16 promise, 'InvalidStateError', 'The device must be opened first.');
19 function assertRejectsWithNotConfiguredError(promise) {
20 return assertRejectsWithError(
21 promise, 'InvalidStateError',
22 'The device must have a configuration selected.');
25 function assertRejectsWithDeviceStateChangeInProgressError(promise) {
26 return assertRejectsWithError(
27 promise, 'InvalidStateError',
28 'An operation that changes the device state is in progress.');
31 function assertRejectsWithInterfaceStateChangeInProgressError(promise) {
32 return assertRejectsWithError(
33 promise, 'InvalidStateError',
34 'An operation that changes interface state is in progress.');
38 return getFakeDevice().then(({ device, fakeDevice }) => {
39 return waitForDisconnect(fakeDevice)
40 .then(() => assertRejectsWithNotFoundError(device.open()));
42 }, 'open rejects when called on a disconnected device');
45 return getFakeDevice().then(({ device, fakeDevice }) => {
47 .then(() => waitForDisconnect(fakeDevice))
49 assert_false(device.opened);
52 }, 'disconnection closes the device');
55 return getFakeDevice().then(({ device }) => {
56 assert_false(device.opened);
57 return device.open().then(() => {
58 assert_true(device.opened);
59 return device.close().then(() => {
60 assert_false(device.opened);
64 }, 'a device can be opened and closed');
67 return getFakeDevice().then(({ device }) => {
69 .then(() => device.open())
70 .then(() => device.open())
71 .then(() => device.open())
72 .then(() => device.close())
73 .then(() => device.close())
74 .then(() => device.close())
75 .then(() => device.close());
77 }, 'open and close can be called multiple times');
79 usb_test(async () => {
80 let { device } = await getFakeDevice();
83 assertRejectsWithDeviceStateChangeInProgressError(device.open()),
84 assertRejectsWithDeviceStateChangeInProgressError(device.close()),
88 assertRejectsWithDeviceStateChangeInProgressError(device.open()),
89 assertRejectsWithDeviceStateChangeInProgressError(device.close()),
91 }, 'open and close cannot be called again while open or close are in progress');
93 usb_test(async () => {
94 let { device } = await getFakeDevice();
97 device.selectConfiguration(1),
98 assertRejectsWithDeviceStateChangeInProgressError(
99 device.claimInterface(0)),
100 assertRejectsWithDeviceStateChangeInProgressError(
101 device.releaseInterface(0)),
102 assertRejectsWithDeviceStateChangeInProgressError(device.open()),
103 assertRejectsWithDeviceStateChangeInProgressError(
104 device.selectConfiguration(1)),
105 assertRejectsWithDeviceStateChangeInProgressError(device.reset()),
106 assertRejectsWithDeviceStateChangeInProgressError(
107 device.selectAlternateInterface(0, 0)),
108 assertRejectsWithDeviceStateChangeInProgressError(
109 device.controlTransferOut({
110 requestType: 'standard',
111 recipient: 'interface',
116 assertRejectsWithDeviceStateChangeInProgressError(
117 device.controlTransferOut({
118 requestType: 'standard',
119 recipient: 'interface',
123 }, new Uint8Array([1, 2, 3]))),
124 assertRejectsWithDeviceStateChangeInProgressError(
125 device.controlTransferIn({
126 requestType: 'standard',
127 recipient: 'interface',
132 assertRejectsWithDeviceStateChangeInProgressError(device.close()),
134 }, 'device operations reject if an device state change is in progress');
137 return getFakeDevice().then(({ device, fakeDevice }) => {
139 .then(() => waitForDisconnect(fakeDevice))
140 .then(() => assertRejectsWithNotFoundError(device.close()));
142 }, 'close rejects when called on a disconnected device');
145 return getFakeDevice().then(({ device, fakeDevice }) => {
147 .then(() => waitForDisconnect(fakeDevice))
148 .then(() => assertRejectsWithNotFoundError(device.selectConfiguration(1)));
150 }, 'selectConfiguration rejects when called on a disconnected device');
153 return getFakeDevice().then(({ device }) => Promise.all([
154 assertRejectsWithNotOpenError(device.selectConfiguration(1)),
155 assertRejectsWithNotOpenError(device.claimInterface(0)),
156 assertRejectsWithNotOpenError(device.releaseInterface(0)),
157 assertRejectsWithNotOpenError(device.selectAlternateInterface(0, 1)),
158 assertRejectsWithNotOpenError(device.controlTransferIn({
159 requestType: 'vendor',
165 assertRejectsWithNotOpenError(device.controlTransferOut({
166 requestType: 'vendor',
171 }, new Uint8Array([1, 2, 3, 4, 5, 6, 7, 8]))),
172 assertRejectsWithNotOpenError(device.clearHalt('in', 1)),
173 assertRejectsWithNotOpenError(device.transferIn(1, 8)),
174 assertRejectsWithNotOpenError(
175 device.transferOut(1, new ArrayBuffer(8))),
176 assertRejectsWithNotOpenError(device.isochronousTransferIn(1, [8])),
177 assertRejectsWithNotOpenError(
178 device.isochronousTransferOut(1, new ArrayBuffer(8), [8])),
179 assertRejectsWithNotOpenError(device.reset())
181 }, 'methods requiring it reject when the device is not open');
184 return getFakeDevice().then(({ device }) => {
185 assert_equals(device.configuration, null);
188 assert_equals(device.configuration, null);
189 return device.selectConfiguration(1);
192 assertDeviceInfoEquals(
193 device.configuration, fakeDeviceInit.configurations[0]);
195 .then(() => device.close());
197 }, 'device configuration can be set and queried');
199 usb_test(async () => {
200 let { device } = await getFakeDevice();
201 assert_equals(device.configuration, null);
203 assert_equals(device.configuration, null);
204 await device.selectConfiguration(1);
205 await device.selectConfiguration(1);
206 assertDeviceInfoEquals(
207 device.configuration, fakeDeviceInit.configurations[0]);
208 await device.selectConfiguration(2);
209 assertDeviceInfoEquals(
210 device.configuration, fakeDeviceInit.configurations[1]);
211 await device.close();
212 }, 'a device configuration value can be set again');
215 return getFakeDevice().then(({ device }) => {
216 assert_equals(device.configuration, null);
218 .then(() => assertRejectsWithError(
219 device.selectConfiguration(3), 'NotFoundError',
220 'The configuration value provided is not supported by the device.'))
221 .then(() => device.close());
223 }, 'selectConfiguration rejects on invalid configurations');
226 return getFakeDevice().then(({ device }) => {
227 assert_equals(device.configuration, null);
228 return device.open().then(() => Promise.all([
229 assertRejectsWithNotConfiguredError(device.claimInterface(0)),
230 assertRejectsWithNotConfiguredError(device.releaseInterface(0)),
231 assertRejectsWithNotConfiguredError(device.selectAlternateInterface(0, 1)),
232 assertRejectsWithNotConfiguredError(device.controlTransferIn({
233 requestType: 'vendor',
239 assertRejectsWithNotConfiguredError(device.controlTransferOut({
240 requestType: 'vendor',
245 }, new Uint8Array([1, 2, 3, 4, 5, 6, 7, 8]))),
246 assertRejectsWithNotConfiguredError(device.clearHalt('in', 1)),
247 assertRejectsWithNotConfiguredError(device.transferIn(1, 8)),
248 assertRejectsWithNotConfiguredError(
249 device.transferOut(1, new ArrayBuffer(8))),
250 assertRejectsWithNotConfiguredError(
251 device.isochronousTransferIn(1, [8])),
252 assertRejectsWithNotConfiguredError(
253 device.isochronousTransferOut(1, new ArrayBuffer(8), [8])),
254 ])).then(() => device.close());
256 }, 'methods requiring it reject when the device is unconfigured');
259 return getFakeDevice().then(({ device }) => {
261 .then(() => device.selectConfiguration(1))
262 .then(() => device.claimInterface(0))
264 assert_true(device.configuration.interfaces[0].claimed);
265 return device.releaseInterface(0);
268 assert_false(device.configuration.interfaces[0].claimed);
269 return device.close();
272 }, 'an interface can be claimed and released');
274 usb_test(async () => {
275 let { device } = await getFakeDevice()
277 await device.selectConfiguration(1);
278 await device.claimInterface(0);
279 assert_true(device.configuration.interfaces[0].claimed);
280 await device.claimInterface(0);
281 assert_true(device.configuration.interfaces[0].claimed);
282 await device.close();
283 }, 'an interface can be claimed multiple times');
285 usb_test(async () => {
286 let { device } = await getFakeDevice();
288 await device.selectConfiguration(1);
289 await device.claimInterface(0);
290 assert_true(device.configuration.interfaces[0].claimed);
291 await device.releaseInterface(0);
292 assert_false(device.configuration.interfaces[0].claimed);
293 await device.releaseInterface(0);
294 assert_false(device.configuration.interfaces[0].claimed);
295 await device.close();
296 }, 'an interface can be released multiple times');
298 usb_test(async () => {
299 let { device } = await getFakeDevice();
301 await device.selectConfiguration(1);
303 device.claimInterface(0),
304 assertRejectsWithInterfaceStateChangeInProgressError(
305 device.claimInterface(0)),
306 assertRejectsWithInterfaceStateChangeInProgressError(
307 device.releaseInterface(0)),
308 assertRejectsWithInterfaceStateChangeInProgressError(device.open()),
309 assertRejectsWithInterfaceStateChangeInProgressError(
310 device.selectConfiguration(1)),
311 assertRejectsWithInterfaceStateChangeInProgressError(device.reset()),
312 assertRejectsWithInterfaceStateChangeInProgressError(
313 device.selectAlternateInterface(0, 0)),
314 assertRejectsWithInterfaceStateChangeInProgressError(
315 device.controlTransferOut({
316 requestType: 'standard',
317 recipient: 'interface',
322 assertRejectsWithInterfaceStateChangeInProgressError(
323 device.controlTransferOut({
324 requestType: 'standard',
325 recipient: 'interface',
329 }, new Uint8Array([1, 2, 3]))),
330 assertRejectsWithInterfaceStateChangeInProgressError(
331 device.controlTransferIn({
332 requestType: 'standard',
333 recipient: 'interface',
338 assertRejectsWithInterfaceStateChangeInProgressError(device.close()),
340 }, 'device operations reject if an interface state change is in progress');
342 usb_test(async () => {
343 let { device } = await getFakeDevice();
345 await device.selectConfiguration(1);
346 await device.claimInterface(0);
347 assert_true(device.configuration.interfaces[0].claimed);
348 await device.close(0);
349 assert_false(device.configuration.interfaces[0].claimed);
350 }, 'interfaces are released on close');
353 return getFakeDevice().then(({ device }) => {
354 const message = 'The interface number provided is not supported by the ' +
355 'device in its current configuration.';
357 .then(() => device.selectConfiguration(1))
358 .then(() => Promise.all([
359 assertRejectsWithError(
360 device.claimInterface(2), 'NotFoundError', message),
361 assertRejectsWithError(
362 device.releaseInterface(2), 'NotFoundError', message),
364 .then(() => device.close());
366 }, 'a non-existent interface cannot be claimed or released');
369 return getFakeDevice().then(({ device, fakeDevice }) => {
371 .then(() => device.selectConfiguration(1))
372 .then(() => waitForDisconnect(fakeDevice))
373 .then(() => assertRejectsWithNotFoundError(device.claimInterface(0)));
375 }, 'claimInterface rejects when called on a disconnected device');
378 return getFakeDevice().then(({ device, fakeDevice }) => {
380 .then(() => device.selectConfiguration(1))
381 .then(() => device.claimInterface(0))
382 .then(() => waitForDisconnect(fakeDevice))
383 .then(() => assertRejectsWithNotFoundError(device.releaseInterface(0)));
385 }, 'releaseInterface rejects when called on a disconnected device');
388 return getFakeDevice().then(({ device }) => {
390 .then(() => device.selectConfiguration(2))
391 .then(() => device.claimInterface(0))
392 .then(() => device.selectAlternateInterface(0, 1))
393 .then(() => device.close());
395 }, 'can select an alternate interface');
398 return getFakeDevice().then(({ device }) => {
400 .then(() => device.selectConfiguration(2))
401 .then(() => device.claimInterface(0))
402 .then(() => assertRejectsWithError(
403 device.selectAlternateInterface(0, 2), 'NotFoundError',
404 'The alternate setting provided is not supported by the device in ' +
405 'its current configuration.'))
406 .then(() => device.close());
408 }, 'cannot select a non-existent alternate interface');
411 return getFakeDevice().then(({ device, fakeDevice }) => {
413 .then(() => device.selectConfiguration(2))
414 .then(() => device.claimInterface(0))
415 .then(() => waitForDisconnect(fakeDevice))
416 .then(() => assertRejectsWithNotFoundError(device.selectAlternateInterface(0, 1)));
418 }, 'selectAlternateInterface rejects when called on a disconnected device');
420 usb_test(async () => {
421 let { device } = await getFakeDevice();
422 let usbRequestTypes = ['standard', 'class', 'vendor'];
423 let usbRecipients = ['device', 'interface', 'endpoint', 'other'];
425 await device.selectConfiguration(1);
426 await device.claimInterface(0);
427 await device.selectAlternateInterface(0, 0);
428 for (const requestType of usbRequestTypes) {
429 for (const recipient of usbRecipients) {
430 let index = recipient === 'interface' ? 0x5600 : 0x5681;
431 let result = await device.controlTransferIn({
432 requestType: requestType,
433 recipient: recipient,
438 assert_true(result instanceof USBInTransferResult);
439 assert_equals(result.status, 'ok');
440 assert_equals(result.data.byteLength, 7);
441 assert_equals(result.data.getUint16(0), 0x07);
442 assert_equals(result.data.getUint8(2), 0x42);
443 assert_equals(result.data.getUint16(3), 0x1234);
444 assert_equals(result.data.getUint16(5), index);
447 await device.close();
448 }, 'can issue all types of IN control transfers');
451 return getFakeDevice().then(({ device, fakeDevice }) => {
453 .then(() => device.selectConfiguration(1))
454 .then(() => waitForDisconnect(fakeDevice))
455 .then(() => assertRejectsWithNotFoundError(device.controlTransferIn({
456 requestType: 'vendor',
463 }, 'controlTransferIn rejects when called on a disconnected device');
465 usb_test(async () => {
466 let { device } = await getFakeDevice();
467 let usbRequestTypes = ['standard', 'class', 'vendor'];
468 let usbRecipients = ['device', 'interface', 'endpoint', 'other'];
469 let dataArray = new Uint8Array([1, 2, 3, 4, 5, 6, 7, 8]);
470 let dataTypes = [dataArray, dataArray.buffer];
472 await device.selectConfiguration(1);
473 await device.claimInterface(0);
474 await device.selectAlternateInterface(0, 0);
475 for (const requestType of usbRequestTypes) {
476 for (const recipient of usbRecipients) {
477 let index = recipient === 'interface' ? 0x5600 : 0x5681;
478 let transferParams = {
479 requestType: requestType,
480 recipient: recipient,
485 for (const data of dataTypes) {
486 let result = await device.controlTransferOut(transferParams, data);
487 assert_true(result instanceof USBOutTransferResult);
488 assert_equals(result.status, 'ok');
489 assert_equals(result.bytesWritten, 8);
491 let result = await device.controlTransferOut(transferParams);
492 assert_true(result instanceof USBOutTransferResult);
493 assert_equals(result.status, 'ok');
496 await device.close();
497 }, 'can issue all types of OUT control transfers');
500 return getFakeDevice().then(({ device, fakeDevice }) => {
502 .then(() => device.selectConfiguration(1))
503 .then(() => waitForDisconnect(fakeDevice))
504 .then(() => assertRejectsWithNotFoundError(device.controlTransferOut({
505 requestType: 'vendor',
510 }, new Uint8Array([1, 2, 3, 4, 5, 6, 7, 8]))));
512 }, 'controlTransferOut rejects when called on a disconnected device');
514 usb_test(async () => {
515 let { device } = await getFakeDevice();
517 await device.selectConfiguration(1);
518 await device.claimInterface(0);
519 assertRejectsWithTypeError(device.controlTransferOut({
520 requestType: 'invalid',
525 }, new Uint8Array([1, 2, 3, 4, 5, 6, 7, 8])));
526 assertRejectsWithTypeError(device.controlTransferIn({
527 requestType: 'invalid',
533 await device.close();
534 }, 'control transfers with a invalid request type reject');
536 usb_test(async () => {
537 let { device } = await getFakeDevice();
539 await device.selectConfiguration(1);
540 await device.claimInterface(0);
541 assertRejectsWithTypeError(device.controlTransferOut({
542 requestType: 'vendor',
543 recipient: 'invalid',
547 }, new Uint8Array([1, 2, 3, 4, 5, 6, 7, 8])));
548 assertRejectsWithTypeError(device.controlTransferIn({
549 requestType: 'vendor',
550 recipient: 'invalid',
555 }, 'control transfers with a invalid recipient type reject');
557 usb_test(async () => {
558 let { device } = await getFakeDevice();
560 await device.selectConfiguration(1);
561 await device.claimInterface(0);
562 assertRejectsWithNotFoundError(device.controlTransferOut({
563 requestType: 'vendor',
564 recipient: 'interface',
567 index: 0x0002 // Last byte of index is interface number.
568 }, new Uint8Array([1, 2, 3, 4, 5, 6, 7, 8])));
569 assertRejectsWithNotFoundError(device.controlTransferIn({
570 requestType: 'vendor',
571 recipient: 'interface',
574 index: 0x0002 // Last byte of index is interface number.
576 }, 'control transfers to a non-existant interface reject');
579 return getFakeDevice().then(({ device }) => {
580 let interfaceRequest = {
581 requestType: 'vendor',
582 recipient: 'interface',
585 index: 0x5600 // Last byte of index is interface number.
587 let endpointRequest = {
588 requestType: 'vendor',
589 recipient: 'endpoint',
592 index: 0x5681 // Last byte of index is endpoint address.
594 let data = new Uint8Array([1, 2, 3, 4, 5, 6, 7, 8]);
596 .then(() => device.selectConfiguration(1))
597 .then(() => Promise.all([
598 assertRejectsWithError(
599 device.controlTransferIn(interfaceRequest, 7),
600 'InvalidStateError'),
601 assertRejectsWithError(
602 device.controlTransferIn(endpointRequest, 7),
604 assertRejectsWithError(
605 device.controlTransferOut(interfaceRequest, data),
606 'InvalidStateError'),
607 assertRejectsWithError(
608 device.controlTransferOut(endpointRequest, data),
611 .then(() => device.claimInterface(0))
612 .then(() => Promise.all([
613 device.controlTransferIn(interfaceRequest, 7).then(result => {
614 assert_true(result instanceof USBInTransferResult);
615 assert_equals(result.status, 'ok');
616 assert_equals(result.data.byteLength, 7);
617 assert_equals(result.data.getUint16(0), 0x07);
618 assert_equals(result.data.getUint8(2), 0x42);
619 assert_equals(result.data.getUint16(3), 0x1234);
620 assert_equals(result.data.getUint16(5), 0x5600);
622 device.controlTransferIn(endpointRequest, 7).then(result => {
623 assert_true(result instanceof USBInTransferResult);
624 assert_equals(result.status, 'ok');
625 assert_equals(result.data.byteLength, 7);
626 assert_equals(result.data.getUint16(0), 0x07);
627 assert_equals(result.data.getUint8(2), 0x42);
628 assert_equals(result.data.getUint16(3), 0x1234);
629 assert_equals(result.data.getUint16(5), 0x5681);
631 device.controlTransferOut(interfaceRequest, data),
632 device.controlTransferOut(endpointRequest, data),
634 .then(() => device.close());
636 }, 'requests to interfaces and endpoint require an interface claim');
639 return getFakeDevice().then(({ device }) => {
641 .then(() => device.selectConfiguration(1))
642 .then(() => device.claimInterface(0))
643 .then(() => device.clearHalt('in', 1))
644 .then(() => device.close());
646 }, 'can clear a halt condition');
649 return getFakeDevice().then(({ device, fakeDevice }) => {
651 .then(() => device.selectConfiguration(1))
652 .then(() => device.claimInterface(0))
653 .then(() => waitForDisconnect(fakeDevice))
654 .then(() => assertRejectsWithNotFoundError(device.clearHalt('in', 1)));
656 }, 'clearHalt rejects when called on a disconnected device');
659 return getFakeDevice().then(({ device }) => {
660 let data = new DataView(new ArrayBuffer(1024));
661 for (let i = 0; i < 1024; ++i)
662 data.setUint8(i, i & 0xff);
663 const notFoundMessage = 'The specified endpoint is not part of a claimed ' +
664 'and selected alternate interface.';
665 const rangeError = 'The specified endpoint number is out of range.';
667 .then(() => device.selectConfiguration(1))
668 .then(() => device.claimInterface(0))
669 .then(() => Promise.all([
670 assertRejectsWithError(device.transferIn(2, 8),
671 'NotFoundError', notFoundMessage), // Unclaimed
672 assertRejectsWithError(device.transferIn(3, 8), 'NotFoundError',
673 notFoundMessage), // Non-existent
674 assertRejectsWithError(
675 device.transferIn(16, 8), 'IndexSizeError', rangeError),
676 assertRejectsWithError(device.transferOut(2, data),
677 'NotFoundError', notFoundMessage), // Unclaimed
678 assertRejectsWithError(device.transferOut(3, data), 'NotFoundError',
679 notFoundMessage), // Non-existent
680 assertRejectsWithError(
681 device.transferOut(16, data), 'IndexSizeError', rangeError),
684 }, 'transfers to unavailable endpoints are rejected');
687 return getFakeDevice().then(({ device }) => {
689 .then(() => device.selectConfiguration(1))
690 .then(() => device.claimInterface(0))
691 .then(() => device.transferIn(1, 8))
693 assert_true(result instanceof USBInTransferResult);
694 assert_equals(result.status, 'ok');
695 assert_equals(result.data.byteLength, 8);
696 for (let i = 0; i < 8; ++i)
697 assert_equals(result.data.getUint8(i), i, 'mismatch at byte ' + i);
698 return device.close();
701 }, 'can issue IN interrupt transfer');
704 return getFakeDevice().then(({ device }) => {
706 .then(() => device.selectConfiguration(1))
707 .then(() => device.claimInterface(1))
708 .then(() => device.transferIn(2, 1024))
710 assert_true(result instanceof USBInTransferResult);
711 assert_equals(result.status, 'ok');
712 assert_equals(result.data.byteLength, 1024);
713 for (let i = 0; i < 1024; ++i)
714 assert_equals(result.data.getUint8(i), i & 0xff,
715 'mismatch at byte ' + i);
716 return device.close();
719 }, 'can issue IN bulk transfer');
722 return getFakeDevice().then(({ device, fakeDevice }) => {
724 .then(() => device.selectConfiguration(1))
725 .then(() => device.claimInterface(1))
726 .then(() => waitForDisconnect(fakeDevice))
727 .then(() => assertRejectsWithNotFoundError(device.transferIn(2, 1024)));
729 }, 'transferIn rejects if called on a disconnected device');
732 return getFakeDevice().then(({ device }) => {
734 .then(() => device.selectConfiguration(1))
735 .then(() => device.claimInterface(1))
737 let data = new DataView(new ArrayBuffer(1024));
738 for (let i = 0; i < 1024; ++i)
739 data.setUint8(i, i & 0xff);
740 return device.transferOut(2, data);
743 assert_true(result instanceof USBOutTransferResult);
744 assert_equals(result.status, 'ok');
745 assert_equals(result.bytesWritten, 1024);
746 return device.close();
749 }, 'can issue OUT bulk transfer');
752 return getFakeDevice().then(({ device, fakeDevice }) => {
754 .then(() => device.selectConfiguration(1))
755 .then(() => device.claimInterface(1))
757 let data = new DataView(new ArrayBuffer(1024));
758 for (let i = 0; i < 1024; ++i)
759 data.setUint8(i, i & 0xff);
760 return waitForDisconnect(fakeDevice)
761 .then(() => assertRejectsWithNotFoundError(device.transferOut(2, data)));
764 }, 'transferOut rejects if called on a disconnected device');
767 return getFakeDevice().then(({ device }) => {
769 .then(() => device.selectConfiguration(2))
770 .then(() => device.claimInterface(0))
771 .then(() => device.selectAlternateInterface(0, 1))
772 .then(() => device.isochronousTransferIn(
773 1, [64, 64, 64, 64, 64, 64, 64, 64]))
775 assert_true(result instanceof USBIsochronousInTransferResult);
776 assert_equals(result.data.byteLength, 64 * 8, 'buffer size');
777 assert_equals(result.packets.length, 8, 'number of packets');
779 for (let i = 0; i < result.packets.length; ++i) {
781 result.packets[i] instanceof USBIsochronousInTransferPacket);
782 assert_equals(result.packets[i].status, 'ok');
783 assert_equals(result.packets[i].data.byteLength, 64);
784 assert_equals(result.packets[i].data.buffer, result.data.buffer);
785 assert_equals(result.packets[i].data.byteOffset, byteOffset);
786 for (let j = 0; j < 64; ++j)
787 assert_equals(result.packets[i].data.getUint8(j), j & 0xff,
788 'mismatch at byte ' + j + ' of packet ' + i);
789 byteOffset += result.packets[i].data.byteLength;
791 return device.close();
794 }, 'can issue IN isochronous transfer');
797 return getFakeDevice().then(({ device, fakeDevice }) => {
799 .then(() => device.selectConfiguration(2))
800 .then(() => device.claimInterface(0))
801 .then(() => device.selectAlternateInterface(0, 1))
802 .then(() => waitForDisconnect(fakeDevice))
803 .then(() => assertRejectsWithNotFoundError(device.isochronousTransferIn(
804 1, [64, 64, 64, 64, 64, 64, 64, 64])));
806 }, 'isochronousTransferIn rejects when called on a disconnected device');
809 return getFakeDevice().then(({ device }) => {
811 .then(() => device.selectConfiguration(2))
812 .then(() => device.claimInterface(0))
813 .then(() => device.selectAlternateInterface(0, 1))
815 let data = new DataView(new ArrayBuffer(64 * 8));
816 for (let i = 0; i < 8; ++i) {
817 for (let j = 0; j < 64; ++j)
818 data.setUint8(i * j, j & 0xff);
820 return device.isochronousTransferOut(
821 1, data, [64, 64, 64, 64, 64, 64, 64, 64]);
824 assert_true(result instanceof USBIsochronousOutTransferResult);
825 assert_equals(result.packets.length, 8, 'number of packets');
827 for (let i = 0; i < result.packets.length; ++i) {
829 result.packets[i] instanceof USBIsochronousOutTransferPacket);
830 assert_equals(result.packets[i].status, 'ok');
831 assert_equals(result.packets[i].bytesWritten, 64);
833 return device.close();
836 }, 'can issue OUT isochronous transfer');
839 return getFakeDevice().then(({ device, fakeDevice }) => {
841 .then(() => device.selectConfiguration(2))
842 .then(() => device.claimInterface(0))
843 .then(() => device.selectAlternateInterface(0, 1))
845 let data = new DataView(new ArrayBuffer(64 * 8));
846 for (let i = 0; i < 8; ++i) {
847 for (let j = 0; j < 64; ++j)
848 data.setUint8(i * j, j & 0xff);
850 return waitForDisconnect(fakeDevice)
851 .then(() => assertRejectsWithNotFoundError(device.isochronousTransferOut(
852 1, data, [64, 64, 64, 64, 64, 64, 64, 64])));
855 }, 'isochronousTransferOut rejects when called on a disconnected device');
858 return getFakeDevice().then(({ device }) => {
859 return device.open().then(() => device.reset()).then(() => device.close());
861 }, 'can reset the device');
864 return getFakeDevice().then(({ device, fakeDevice }) => {
866 .then(() => waitForDisconnect(fakeDevice))
867 .then(() => assertRejectsWithNotFoundError(device.reset()));
869 }, 'resetDevice rejects when called on a disconnected device');