libusb 0.5.0 → 0.5.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (141) hide show
  1. checksums.yaml +4 -4
  2. checksums.yaml.gz.sig +0 -0
  3. data.tar.gz.sig +0 -0
  4. data/.travis.yml +1 -0
  5. data/History.md +8 -0
  6. data/README.md +5 -15
  7. data/Rakefile +8 -1
  8. data/ext/extconf.rb +49 -12
  9. data/ext/{libusb-1.0.19 → libusb-1.0.20}/AUTHORS +12 -1
  10. data/ext/{libusb-1.0.19 → libusb-1.0.20}/COPYING +0 -0
  11. data/ext/{libusb-1.0.19 → libusb-1.0.20}/ChangeLog +18 -2
  12. data/ext/{libusb-1.0.19 → libusb-1.0.20}/INSTALL +0 -0
  13. data/ext/{libusb-1.0.19 → libusb-1.0.20}/Makefile.am +0 -0
  14. data/ext/{libusb-1.0.19 → libusb-1.0.20}/Makefile.in +31 -18
  15. data/ext/{libusb-1.0.19 → libusb-1.0.20}/NEWS +0 -0
  16. data/ext/{libusb-1.0.19 → libusb-1.0.20}/PORTING +0 -0
  17. data/ext/{libusb-1.0.19 → libusb-1.0.20}/README +5 -3
  18. data/ext/{libusb-1.0.19 → libusb-1.0.20}/TODO +0 -0
  19. data/ext/{libusb-1.0.19 → libusb-1.0.20}/Xcode/common.xcconfig +0 -0
  20. data/ext/{libusb-1.0.19 → libusb-1.0.20}/Xcode/config.h +0 -0
  21. data/ext/{libusb-1.0.19 → libusb-1.0.20}/Xcode/debug.xcconfig +0 -0
  22. data/ext/{libusb-1.0.19 → libusb-1.0.20}/Xcode/libusb.xcconfig +0 -0
  23. data/ext/libusb-1.0.20/Xcode/libusb.xcodeproj/project.pbxproj +865 -0
  24. data/ext/{libusb-1.0.19 → libusb-1.0.20}/Xcode/libusb_debug.xcconfig +0 -0
  25. data/ext/{libusb-1.0.19 → libusb-1.0.20}/Xcode/libusb_release.xcconfig +0 -0
  26. data/ext/{libusb-1.0.19 → libusb-1.0.20}/Xcode/release.xcconfig +0 -0
  27. data/ext/{libusb-1.0.19 → libusb-1.0.20}/aclocal.m4 +35 -32
  28. data/ext/{libusb-1.0.19 → libusb-1.0.20}/android/README +0 -0
  29. data/ext/{libusb-1.0.19 → libusb-1.0.20}/android/config.h +0 -0
  30. data/ext/{libusb-1.0.19 → libusb-1.0.20}/android/jni/Android.mk +0 -0
  31. data/ext/{libusb-1.0.19 → libusb-1.0.20}/android/jni/Application.mk +0 -0
  32. data/ext/{libusb-1.0.19 → libusb-1.0.20}/android/jni/examples.mk +0 -0
  33. data/ext/{libusb-1.0.19 → libusb-1.0.20}/android/jni/libusb.mk +0 -0
  34. data/ext/{libusb-1.0.19 → libusb-1.0.20}/android/jni/tests.mk +0 -0
  35. data/ext/{libusb-1.0.19 → libusb-1.0.20}/compile +1 -1
  36. data/ext/{libusb-1.0.19 → libusb-1.0.20}/config.guess +13 -160
  37. data/ext/{libusb-1.0.19 → libusb-1.0.20}/config.h.in +6 -0
  38. data/ext/{libusb-1.0.19 → libusb-1.0.20}/config.sub +26 -12
  39. data/ext/{libusb-1.0.19 → libusb-1.0.20}/configure +244 -20
  40. data/ext/{libusb-1.0.19 → libusb-1.0.20}/configure.ac +27 -4
  41. data/ext/{libusb-1.0.19 → libusb-1.0.20}/depcomp +1 -1
  42. data/ext/{libusb-1.0.19 → libusb-1.0.20}/doc/Makefile.am +0 -0
  43. data/ext/{libusb-1.0.19 → libusb-1.0.20}/doc/Makefile.in +19 -6
  44. data/ext/libusb-1.0.20/doc/doxygen.cfg.in +2334 -0
  45. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/Makefile.am +0 -0
  46. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/Makefile.in +19 -6
  47. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/dpfp.c +0 -0
  48. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/dpfp_threaded.c +15 -10
  49. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/ezusb.c +0 -0
  50. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/ezusb.h +0 -0
  51. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/fxload.c +28 -7
  52. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/getopt/getopt.c +0 -0
  53. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/getopt/getopt.h +0 -0
  54. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/getopt/getopt1.c +0 -0
  55. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/hotplugtest.c +21 -3
  56. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/listdevs.c +0 -0
  57. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/sam3u_benchmark.c +0 -0
  58. data/ext/{libusb-1.0.19 → libusb-1.0.20}/examples/xusb.c +2 -1
  59. data/ext/{libusb-1.0.19 → libusb-1.0.20}/install-sh +170 -196
  60. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb-1.0.pc.in +0 -0
  61. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/Makefile.am +15 -0
  62. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/Makefile.in +192 -53
  63. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/core.c +218 -100
  64. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/descriptor.c +3 -1
  65. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/hotplug.c +26 -9
  66. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/hotplug.h +8 -0
  67. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/io.c +432 -290
  68. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/libusb-1.0.def +2 -0
  69. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/libusb-1.0.rc +0 -0
  70. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/libusb.h +11 -10
  71. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/libusbi.h +106 -29
  72. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/darwin_usb.c +27 -67
  73. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/darwin_usb.h +3 -7
  74. data/ext/libusb-1.0.20/libusb/os/haiku/Makefile.am +5 -0
  75. data/ext/libusb-1.0.20/libusb/os/haiku/Makefile.in +810 -0
  76. data/ext/libusb-1.0.20/libusb/os/haiku/aclocal.m4 +1193 -0
  77. data/ext/libusb-1.0.20/libusb/os/haiku/compile +347 -0
  78. data/ext/libusb-1.0.20/libusb/os/haiku/config.guess +1421 -0
  79. data/ext/libusb-1.0.20/libusb/os/haiku/config.sub +1807 -0
  80. data/ext/libusb-1.0.20/libusb/os/haiku/configure +17579 -0
  81. data/ext/libusb-1.0.20/libusb/os/haiku/configure.ac +8 -0
  82. data/ext/libusb-1.0.20/libusb/os/haiku/depcomp +791 -0
  83. data/ext/libusb-1.0.20/libusb/os/haiku/haiku_pollfs.cpp +378 -0
  84. data/ext/libusb-1.0.20/libusb/os/haiku/haiku_usb.h +112 -0
  85. data/ext/libusb-1.0.20/libusb/os/haiku/haiku_usb_backend.cpp +550 -0
  86. data/ext/libusb-1.0.20/libusb/os/haiku/haiku_usb_raw.cpp +255 -0
  87. data/ext/libusb-1.0.20/libusb/os/haiku/haiku_usb_raw.h +180 -0
  88. data/ext/libusb-1.0.20/libusb/os/haiku/install-sh +501 -0
  89. data/ext/{libusb-1.0.19 → libusb-1.0.20/libusb/os/haiku}/ltmain.sh +0 -0
  90. data/ext/{libusb-1.0.19 → libusb-1.0.20/libusb/os/haiku}/m4/libtool.m4 +0 -0
  91. data/ext/{libusb-1.0.19 → libusb-1.0.20/libusb/os/haiku}/m4/ltoptions.m4 +0 -0
  92. data/ext/{libusb-1.0.19 → libusb-1.0.20/libusb/os/haiku}/m4/ltsugar.m4 +0 -0
  93. data/ext/{libusb-1.0.19 → libusb-1.0.20/libusb/os/haiku}/m4/ltversion.m4 +0 -0
  94. data/ext/{libusb-1.0.19 → libusb-1.0.20/libusb/os/haiku}/m4/lt~obsolete.m4 +0 -0
  95. data/ext/{libusb-1.0.19 → libusb-1.0.20/libusb/os/haiku}/missing +1 -1
  96. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/linux_netlink.c +4 -4
  97. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/linux_udev.c +1 -2
  98. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/linux_usbfs.c +46 -49
  99. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/linux_usbfs.h +1 -1
  100. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/netbsd_usb.c +9 -73
  101. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/openbsd_usb.c +9 -73
  102. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/poll_posix.c +2 -0
  103. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/poll_posix.h +0 -0
  104. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/poll_windows.c +3 -1
  105. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/poll_windows.h +0 -0
  106. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/threads_posix.c +3 -3
  107. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/threads_posix.h +0 -0
  108. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/threads_windows.c +3 -1
  109. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/threads_windows.h +0 -0
  110. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/wince_usb.c +87 -250
  111. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/wince_usb.h +0 -0
  112. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/windows_common.h +1 -1
  113. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/windows_usb.c +267 -181
  114. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/os/windows_usb.h +22 -7
  115. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/strerror.c +5 -2
  116. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/sync.c +2 -1
  117. data/ext/{libusb-1.0.19 → libusb-1.0.20}/libusb/version.h +1 -1
  118. data/ext/libusb-1.0.20/libusb/version_nano.h +1 -0
  119. data/ext/libusb-1.0.20/ltmain.sh +9655 -0
  120. data/ext/libusb-1.0.20/m4/libtool.m4 +7992 -0
  121. data/ext/libusb-1.0.20/m4/ltoptions.m4 +384 -0
  122. data/ext/libusb-1.0.20/m4/ltsugar.m4 +123 -0
  123. data/ext/libusb-1.0.20/m4/ltversion.m4 +23 -0
  124. data/ext/libusb-1.0.20/m4/lt~obsolete.m4 +98 -0
  125. data/ext/libusb-1.0.20/missing +215 -0
  126. data/ext/{libusb-1.0.19 → libusb-1.0.20}/tests/Makefile.am +0 -0
  127. data/ext/{libusb-1.0.19 → libusb-1.0.20}/tests/Makefile.in +19 -6
  128. data/ext/{libusb-1.0.19 → libusb-1.0.20}/tests/libusb_testlib.h +0 -0
  129. data/ext/{libusb-1.0.19 → libusb-1.0.20}/tests/stress.c +0 -0
  130. data/ext/{libusb-1.0.19 → libusb-1.0.20}/tests/testlib.c +0 -0
  131. data/lib/libusb.rb +1 -0
  132. data/lib/libusb/call.rb +1 -0
  133. data/lib/libusb/context.rb +5 -2
  134. data/lib/libusb/stdio.rb +25 -0
  135. data/lib/libusb/version_gem.rb +1 -1
  136. data/libusb.gemspec +2 -1
  137. metadata +152 -115
  138. metadata.gz.sig +0 -0
  139. data/ext/libusb-1.0.19/Xcode/libusb.xcodeproj/project.pbxproj +0 -1
  140. data/ext/libusb-1.0.19/doc/doxygen.cfg.in +0 -1288
  141. data/ext/libusb-1.0.19/libusb/version_nano.h +0 -1
@@ -0,0 +1,550 @@
1
+ /*
2
+ * Haiku Backend for libusb
3
+ * Copyright © 2014 Akshay Jaggi <akshay1994.leo@gmail.com>
4
+ *
5
+ * This library is free software; you can redistribute it and/or
6
+ * modify it under the terms of the GNU Lesser General Public
7
+ * License as published by the Free Software Foundation; either
8
+ * version 2.1 of the License, or (at your option) any later version.
9
+ *
10
+ * This library is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13
+ * Lesser General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU Lesser General Public
16
+ * License along with this library; if not, write to the Free Software
17
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18
+ */
19
+
20
+
21
+ #include <unistd.h>
22
+ #include <string.h>
23
+ #include <stdlib.h>
24
+ #include <new>
25
+ #include <vector>
26
+
27
+ #include "haiku_usb.h"
28
+
29
+ int _errno_to_libusb(int status)
30
+ {
31
+ return status;
32
+ }
33
+
34
+ USBTransfer::USBTransfer(struct usbi_transfer* itransfer, USBDevice* device)
35
+ {
36
+ fUsbiTransfer=itransfer;
37
+ fLibusbTransfer=USBI_TRANSFER_TO_LIBUSB_TRANSFER(itransfer);
38
+ fUSBDevice=device;
39
+ fCancelled=false;
40
+ }
41
+
42
+ USBTransfer::~USBTransfer()
43
+ {
44
+ }
45
+
46
+ struct usbi_transfer*
47
+ USBTransfer::UsbiTransfer()
48
+ {
49
+ return fUsbiTransfer;
50
+ }
51
+
52
+ void
53
+ USBTransfer::SetCancelled()
54
+ {
55
+ fCancelled=true;
56
+ }
57
+
58
+ bool
59
+ USBTransfer::IsCancelled()
60
+ {
61
+ return fCancelled;
62
+ }
63
+
64
+ void
65
+ USBTransfer::Do(int fRawFD)
66
+ {
67
+ switch(fLibusbTransfer->type)
68
+ {
69
+ case LIBUSB_TRANSFER_TYPE_CONTROL:
70
+ {
71
+ struct libusb_control_setup* setup=(struct libusb_control_setup*)fLibusbTransfer->buffer;
72
+ usb_raw_command command;
73
+ command.control.request_type=setup->bmRequestType;
74
+ command.control.request=setup->bRequest;
75
+ command.control.value=setup->wValue;
76
+ command.control.index=setup->wIndex;
77
+ command.control.length=setup->wLength;
78
+ command.control.data=fLibusbTransfer->buffer + LIBUSB_CONTROL_SETUP_SIZE;
79
+ if(fCancelled)
80
+ {
81
+ break;
82
+ }
83
+ if(ioctl(fRawFD,B_USB_RAW_COMMAND_CONTROL_TRANSFER,&command,
84
+ sizeof(command)) || command.control.status!=B_USB_RAW_STATUS_SUCCESS) {
85
+ fUsbiTransfer->transferred=-1;
86
+ usbi_err(TRANSFER_CTX(fLibusbTransfer),"failed control transfer");
87
+ break;
88
+ }
89
+ fUsbiTransfer->transferred=command.control.length;
90
+ }
91
+ break;
92
+ case LIBUSB_TRANSFER_TYPE_BULK:
93
+ case LIBUSB_TRANSFER_TYPE_INTERRUPT:
94
+ {
95
+ usb_raw_command command;
96
+ command.transfer.interface=fUSBDevice->EndpointToInterface(fLibusbTransfer->endpoint);
97
+ command.transfer.endpoint=fUSBDevice->EndpointToIndex(fLibusbTransfer->endpoint);
98
+ command.transfer.data=fLibusbTransfer->buffer;
99
+ command.transfer.length=fLibusbTransfer->length;
100
+ if(fCancelled)
101
+ {
102
+ break;
103
+ }
104
+ if(fLibusbTransfer->type==LIBUSB_TRANSFER_TYPE_BULK)
105
+ {
106
+ if(ioctl(fRawFD,B_USB_RAW_COMMAND_BULK_TRANSFER,&command,
107
+ sizeof(command)) || command.transfer.status!=B_USB_RAW_STATUS_SUCCESS) {
108
+ fUsbiTransfer->transferred=-1;
109
+ usbi_err(TRANSFER_CTX(fLibusbTransfer),"failed bulk transfer");
110
+ break;
111
+ }
112
+ }
113
+ else
114
+ {
115
+ if(ioctl(fRawFD,B_USB_RAW_COMMAND_INTERRUPT_TRANSFER,&command,
116
+ sizeof(command)) || command.transfer.status!=B_USB_RAW_STATUS_SUCCESS) {
117
+ fUsbiTransfer->transferred=-1;
118
+ usbi_err(TRANSFER_CTX(fLibusbTransfer),"failed interrupt transfer");
119
+ break;
120
+ }
121
+ }
122
+ fUsbiTransfer->transferred=command.transfer.length;
123
+ }
124
+ break;
125
+ // IsochronousTransfers not tested
126
+ case LIBUSB_TRANSFER_TYPE_ISOCHRONOUS:
127
+ {
128
+ usb_raw_command command;
129
+ command.isochronous.interface=fUSBDevice->EndpointToInterface(fLibusbTransfer->endpoint);
130
+ command.isochronous.endpoint=fUSBDevice->EndpointToIndex(fLibusbTransfer->endpoint);
131
+ command.isochronous.data=fLibusbTransfer->buffer;
132
+ command.isochronous.length=fLibusbTransfer->length;
133
+ command.isochronous.packet_count=fLibusbTransfer->num_iso_packets;
134
+ int i=0;
135
+ usb_iso_packet_descriptor *packetDescriptors = new usb_iso_packet_descriptor[fLibusbTransfer->num_iso_packets];
136
+ for (i=0; i<fLibusbTransfer->num_iso_packets; i++)
137
+ {
138
+ if((int16)(fLibusbTransfer->iso_packet_desc[i]).length!=(fLibusbTransfer->iso_packet_desc[i]).length)
139
+ {
140
+ fUsbiTransfer->transferred=-1;
141
+ usbi_err(TRANSFER_CTX(fLibusbTransfer),"failed isochronous transfer");
142
+ break;
143
+ }
144
+ packetDescriptors[i].request_length=(int16)(fLibusbTransfer->iso_packet_desc[i]).length;
145
+ }
146
+ if(i<fLibusbTransfer->num_iso_packets)
147
+ {
148
+ break; // TODO Handle this error
149
+ }
150
+ command.isochronous.packet_descriptors=packetDescriptors;
151
+ if(fCancelled)
152
+ {
153
+ break;
154
+ }
155
+ if(ioctl(fRawFD,B_USB_RAW_COMMAND_ISOCHRONOUS_TRANSFER,&command,
156
+ sizeof(command)) || command.isochronous.status!=B_USB_RAW_STATUS_SUCCESS) {
157
+ fUsbiTransfer->transferred=-1;
158
+ usbi_err(TRANSFER_CTX(fLibusbTransfer),"failed isochronous transfer");
159
+ break;
160
+ }
161
+ for (i=0; i<fLibusbTransfer->num_iso_packets; i++)
162
+ {
163
+ (fLibusbTransfer->iso_packet_desc[i]).actual_length=packetDescriptors[i].actual_length;
164
+ switch(packetDescriptors[i].status)
165
+ {
166
+ case B_OK: (fLibusbTransfer->iso_packet_desc[i]).status=LIBUSB_TRANSFER_COMPLETED;
167
+ break;
168
+ default: (fLibusbTransfer->iso_packet_desc[i]).status=LIBUSB_TRANSFER_ERROR;
169
+ break;
170
+ }
171
+ }
172
+ delete[] packetDescriptors;
173
+ // Do we put the length of transfer here, for isochronous transfers?
174
+ fUsbiTransfer->transferred=command.transfer.length;
175
+ }
176
+ break;
177
+ default:
178
+ usbi_err(TRANSFER_CTX(fLibusbTransfer),"Unknown type of transfer");
179
+ }
180
+ }
181
+
182
+ bool
183
+ USBDeviceHandle::InitCheck()
184
+ {
185
+ return fInitCheck;
186
+ }
187
+
188
+ status_t
189
+ USBDeviceHandle::TransfersThread(void* self)
190
+ {
191
+ USBDeviceHandle* handle = (USBDeviceHandle*)self;
192
+ handle->TransfersWorker();
193
+ return B_OK;
194
+ }
195
+
196
+ void
197
+ USBDeviceHandle::TransfersWorker()
198
+ {
199
+ while(true)
200
+ {
201
+ status_t status = acquire_sem(fTransfersSem);
202
+ if(status== B_BAD_SEM_ID)
203
+ break;
204
+ if(status == B_INTERRUPTED)
205
+ continue;
206
+ fTransfersLock.Lock();
207
+ USBTransfer* fPendingTransfer= (USBTransfer*) fTransfers.RemoveItem((int32)0);
208
+ fTransfersLock.Unlock();
209
+ fPendingTransfer->Do(fRawFD);
210
+ usbi_signal_transfer_completion(fPendingTransfer->UsbiTransfer());
211
+ }
212
+ }
213
+
214
+ status_t
215
+ USBDeviceHandle::SubmitTransfer(struct usbi_transfer* itransfer)
216
+ {
217
+ USBTransfer* transfer = new USBTransfer(itransfer,fUSBDevice);
218
+ *((USBTransfer**)usbi_transfer_get_os_priv(itransfer))=transfer;
219
+ BAutolock locker(fTransfersLock);
220
+ fTransfers.AddItem(transfer);
221
+ release_sem(fTransfersSem);
222
+ return LIBUSB_SUCCESS;
223
+ }
224
+
225
+ status_t
226
+ USBDeviceHandle::CancelTransfer(USBTransfer* transfer)
227
+ {
228
+ transfer->SetCancelled();
229
+ fTransfersLock.Lock();
230
+ bool removed = fTransfers.RemoveItem(transfer);
231
+ fTransfersLock.Unlock();
232
+ if(removed)
233
+ {
234
+ usbi_signal_transfer_completion(transfer->UsbiTransfer());
235
+ }
236
+ return LIBUSB_SUCCESS;
237
+ }
238
+
239
+ USBDeviceHandle::USBDeviceHandle(USBDevice* dev)
240
+ :
241
+ fTransfersThread(-1),
242
+ fUSBDevice(dev),
243
+ fClaimedInterfaces(0),
244
+ fInitCheck(false)
245
+ {
246
+ fRawFD=open(dev->Location(), O_RDWR | O_CLOEXEC);
247
+ if(fRawFD < 0)
248
+ {
249
+ usbi_err(NULL,"failed to open device");
250
+ return;
251
+ }
252
+ fTransfersSem = create_sem(0, "Transfers Queue Sem");
253
+ fTransfersThread = spawn_thread(TransfersThread,"Transfer Worker",B_NORMAL_PRIORITY, this);
254
+ resume_thread(fTransfersThread);
255
+ fInitCheck = true;
256
+ }
257
+
258
+ USBDeviceHandle::~USBDeviceHandle()
259
+ {
260
+ if(fRawFD>0)
261
+ close(fRawFD);
262
+ for(int i=0; i<32; i++)
263
+ {
264
+ if(fClaimedInterfaces&(1<<i))
265
+ ReleaseInterface(i);
266
+ }
267
+ delete_sem(fTransfersSem);
268
+ if(fTransfersThread>0)
269
+ wait_for_thread(fTransfersThread, NULL);
270
+ }
271
+
272
+ int
273
+ USBDeviceHandle::ClaimInterface(int inumber)
274
+ {
275
+ int status=fUSBDevice->ClaimInterface(inumber);
276
+ if(status==LIBUSB_SUCCESS)
277
+ {
278
+ fClaimedInterfaces|=(1<<inumber);
279
+ }
280
+ return status;
281
+ }
282
+
283
+ int
284
+ USBDeviceHandle::ReleaseInterface(int inumber)
285
+ {
286
+ fUSBDevice->ReleaseInterface(inumber);
287
+ fClaimedInterfaces&=(!(1<<inumber));
288
+ return LIBUSB_SUCCESS;
289
+ }
290
+
291
+ int
292
+ USBDeviceHandle::SetConfiguration(int config)
293
+ {
294
+ int config_index=fUSBDevice->CheckInterfacesFree(config);
295
+ if(config_index==LIBUSB_ERROR_BUSY || config_index==LIBUSB_ERROR_NOT_FOUND)
296
+ return config_index;
297
+
298
+ usb_raw_command command;
299
+ command.config.config_index=config_index;
300
+ if(ioctl(fRawFD,B_USB_RAW_COMMAND_SET_CONFIGURATION,&command,
301
+ sizeof(command)) || command.config.status != B_USB_RAW_STATUS_SUCCESS) {
302
+ return _errno_to_libusb(command.config.status);
303
+ }
304
+ fUSBDevice->SetActiveConfiguration(config_index);
305
+ return LIBUSB_SUCCESS;
306
+ }
307
+
308
+ int
309
+ USBDeviceHandle::SetAltSetting(int inumber, int alt)
310
+ {
311
+ usb_raw_command command;
312
+ command.alternate.config_index=fUSBDevice->ActiveConfigurationIndex();
313
+ command.alternate.interface_index=inumber;
314
+ if(ioctl(fRawFD,B_USB_RAW_COMMAND_GET_ACTIVE_ALT_INTERFACE_INDEX,&command,
315
+ sizeof(command)) || command.alternate.status!=B_USB_RAW_STATUS_SUCCESS) {
316
+ usbi_err(NULL,"Error retrieving active alternate interface");
317
+ return _errno_to_libusb(command.alternate.status);
318
+ }
319
+ if(command.alternate.alternate_info == alt)
320
+ {
321
+ usbi_dbg("Setting alternate interface successful");
322
+ return LIBUSB_SUCCESS;
323
+ }
324
+ command.alternate.alternate_info = alt;
325
+ if(ioctl(fRawFD,B_USB_RAW_COMMAND_SET_ALT_INTERFACE,&command, //IF IOCTL FAILS DEVICE DISONNECTED PROBABLY
326
+ sizeof(command)) || command.alternate.status!=B_USB_RAW_STATUS_SUCCESS) {
327
+ usbi_err(NULL,"Error setting alternate interface");
328
+ return _errno_to_libusb(command.alternate.status);
329
+ }
330
+ usbi_dbg("Setting alternate interface successful");
331
+ return LIBUSB_SUCCESS;
332
+ }
333
+
334
+
335
+ USBDevice::USBDevice(const char * path)
336
+ :
337
+ fPath(NULL),
338
+ fActiveConfiguration(0), //0?
339
+ fConfigurationDescriptors(NULL),
340
+ fClaimedInterfaces(0),
341
+ fEndpointToIndex(NULL),
342
+ fEndpointToInterface(NULL),
343
+ fInitCheck(false)
344
+ {
345
+ fPath=strdup(path);
346
+ Initialise();
347
+ }
348
+
349
+ USBDevice::~USBDevice()
350
+ {
351
+ free(fPath);
352
+ if (fConfigurationDescriptors)
353
+ {
354
+ for(int i=0;i<fDeviceDescriptor.num_configurations;i++)
355
+ {
356
+ if (fConfigurationDescriptors[i])
357
+ delete fConfigurationDescriptors[i];
358
+ }
359
+ delete[] fConfigurationDescriptors;
360
+ }
361
+ if (fEndpointToIndex)
362
+ delete[] fEndpointToIndex;
363
+ if (fEndpointToInterface)
364
+ delete[] fEndpointToInterface;
365
+ }
366
+
367
+ bool
368
+ USBDevice::InitCheck()
369
+ {
370
+ return fInitCheck;
371
+ }
372
+
373
+ const char*
374
+ USBDevice::Location() const
375
+ {
376
+ return fPath;
377
+ }
378
+
379
+ uint8
380
+ USBDevice::CountConfigurations() const
381
+ {
382
+ return fDeviceDescriptor.num_configurations;
383
+ }
384
+
385
+ const usb_device_descriptor*
386
+ USBDevice::Descriptor() const
387
+ {
388
+ return &fDeviceDescriptor;
389
+ }
390
+
391
+ const usb_configuration_descriptor*
392
+ USBDevice::ConfigurationDescriptor(uint32 index) const
393
+ {
394
+ if(index>CountConfigurations())
395
+ return NULL;
396
+ return (usb_configuration_descriptor*) fConfigurationDescriptors[index];
397
+ }
398
+
399
+ const usb_configuration_descriptor*
400
+ USBDevice::ActiveConfiguration() const
401
+ {
402
+ return (usb_configuration_descriptor*) fConfigurationDescriptors[fActiveConfiguration];
403
+ }
404
+
405
+ int
406
+ USBDevice::ActiveConfigurationIndex() const
407
+ {
408
+ return fActiveConfiguration;
409
+ }
410
+
411
+ int USBDevice::ClaimInterface(int interface)
412
+ {
413
+ if(interface>ActiveConfiguration()->number_interfaces)
414
+ {
415
+ return LIBUSB_ERROR_NOT_FOUND;
416
+ }
417
+ if((fClaimedInterfaces & (1<<interface)) !=0 )
418
+ return LIBUSB_ERROR_BUSY;
419
+ fClaimedInterfaces|=(1<<interface);
420
+ return LIBUSB_SUCCESS;
421
+ }
422
+
423
+ int USBDevice::ReleaseInterface(int interface)
424
+ {
425
+ fClaimedInterfaces&=(!(1<<interface));
426
+ return LIBUSB_SUCCESS;
427
+ }
428
+
429
+ int
430
+ USBDevice::CheckInterfacesFree(int config)
431
+ {
432
+ if(fConfigToIndex.count(config)==0)
433
+ return LIBUSB_ERROR_NOT_FOUND;
434
+ if(fClaimedInterfaces==0)
435
+ return fConfigToIndex[(uint8)config];
436
+ return LIBUSB_ERROR_BUSY;
437
+ }
438
+
439
+ int
440
+ USBDevice::SetActiveConfiguration(int config_index)
441
+ {
442
+ fActiveConfiguration=config_index;
443
+ return LIBUSB_SUCCESS;
444
+ }
445
+
446
+ uint8
447
+ USBDevice::EndpointToIndex(uint8 address) const
448
+ {
449
+ return fEndpointToIndex[fActiveConfiguration][address];
450
+ }
451
+
452
+ uint8
453
+ USBDevice::EndpointToInterface(uint8 address) const
454
+ {
455
+ return fEndpointToInterface[fActiveConfiguration][address];
456
+ }
457
+
458
+ int
459
+ USBDevice::Initialise() //Do we need more error checking, etc? How to report?
460
+ {
461
+ int fRawFD=open(fPath, O_RDWR | O_CLOEXEC);
462
+ if(fRawFD < 0)
463
+ return B_ERROR;
464
+
465
+ usb_raw_command command;
466
+ command.device.descriptor = &fDeviceDescriptor;
467
+ if(ioctl(fRawFD, B_USB_RAW_COMMAND_GET_DEVICE_DESCRIPTOR, &command,
468
+ sizeof(command)) || command.device.status != B_USB_RAW_STATUS_SUCCESS) {
469
+ close(fRawFD);
470
+ return B_ERROR;
471
+ }
472
+
473
+ size_t size;
474
+ fConfigurationDescriptors = new(std::nothrow) unsigned char*[fDeviceDescriptor.num_configurations];
475
+ fEndpointToIndex = new(std::nothrow) map<uint8,uint8> [fDeviceDescriptor.num_configurations];
476
+ fEndpointToInterface = new(std::nothrow) map<uint8,uint8> [fDeviceDescriptor.num_configurations];
477
+ for( int i=0; i<fDeviceDescriptor.num_configurations; i++)
478
+ {
479
+ size=0;
480
+ usb_configuration_descriptor tmp_config;
481
+ command.config.descriptor = &tmp_config;
482
+ command.config.config_index = i;
483
+ if(ioctl(fRawFD, B_USB_RAW_COMMAND_GET_CONFIGURATION_DESCRIPTOR, &command,
484
+ sizeof(command)) || command.config.status != B_USB_RAW_STATUS_SUCCESS) {
485
+ usbi_err(NULL,"failed retrieving configuration descriptor");
486
+ close(fRawFD);
487
+ return B_ERROR;
488
+ }
489
+ fConfigToIndex[tmp_config.configuration_value]=i;
490
+ fConfigurationDescriptors[i]=new(std::nothrow) unsigned char[tmp_config.total_length];
491
+ command.control.request_type=128;
492
+ command.control.request=6;
493
+ command.control.value=(2<<8)|i;
494
+ command.control.index=0;
495
+ command.control.length=tmp_config.total_length;
496
+ command.control.data=fConfigurationDescriptors[i];
497
+ if(ioctl(fRawFD,B_USB_RAW_COMMAND_CONTROL_TRANSFER,&command,
498
+ sizeof(command)) || command.control.status!=B_USB_RAW_STATUS_SUCCESS) {
499
+ usbi_err(NULL,"failed retrieving full configuration descriptor");
500
+ close(fRawFD);
501
+ return B_ERROR;
502
+ }
503
+ for( int j=0;j<tmp_config.number_interfaces;j++)
504
+ {
505
+ command.alternate.config_index=i;
506
+ command.alternate.interface_index=j;
507
+ if(ioctl(fRawFD,B_USB_RAW_COMMAND_GET_ALT_INTERFACE_COUNT, &command,
508
+ sizeof(command)) || command.config.status != B_USB_RAW_STATUS_SUCCESS) {
509
+ usbi_err(NULL,"failed retrieving number of alternate interfaces");
510
+ close(fRawFD);
511
+ return B_ERROR;
512
+ }
513
+ int num_alternate=command.alternate.alternate_info;
514
+ for( int k=0;k<num_alternate;k++)
515
+ {
516
+ usb_interface_descriptor tmp_interface;
517
+ command.interface_etc.config_index=i;
518
+ command.interface_etc.interface_index=j;
519
+ command.interface_etc.alternate_index=k;
520
+ command.interface_etc.descriptor=&tmp_interface;
521
+ if(ioctl(fRawFD,B_USB_RAW_COMMAND_GET_INTERFACE_DESCRIPTOR_ETC, &command,
522
+ sizeof(command)) || command.config.status != B_USB_RAW_STATUS_SUCCESS) {
523
+ usbi_err(NULL,"failed retrieving interface descriptor");
524
+ close(fRawFD);
525
+ return B_ERROR;
526
+ }
527
+ for( int l=0;l<tmp_interface.num_endpoints;l++)
528
+ {
529
+ usb_endpoint_descriptor tmp_endpoint;
530
+ command.endpoint_etc.config_index=i;
531
+ command.endpoint_etc.interface_index=j;
532
+ command.endpoint_etc.alternate_index=k;
533
+ command.endpoint_etc.endpoint_index=l;
534
+ command.endpoint_etc.descriptor=&tmp_endpoint;
535
+ if(ioctl(fRawFD,B_USB_RAW_COMMAND_GET_ENDPOINT_DESCRIPTOR_ETC, &command,
536
+ sizeof(command)) || command.config.status != B_USB_RAW_STATUS_SUCCESS) {
537
+ usbi_err(NULL,"failed retrieving endpoint descriptor");
538
+ close(fRawFD);
539
+ return B_ERROR;
540
+ }
541
+ fEndpointToIndex[i][tmp_endpoint.endpoint_address]=l;
542
+ fEndpointToInterface[i][tmp_endpoint.endpoint_address]=j;
543
+ }
544
+ }
545
+ }
546
+ }
547
+ close(fRawFD);
548
+ fInitCheck = true;
549
+ return B_OK;
550
+ }