mirror of https://github.com/GOSTSec/sgminer
Con Kolivas
11 years ago
54 changed files with 8800 additions and 3626 deletions
@ -1,46 +1,62 @@
@@ -1,46 +1,62 @@
|
||||
Copyright (C) 2007-2009 Daniel Drake <dsd@gentoo.org> |
||||
Copyright (c) 2001 Johannes Erdfelt <johannes@erdfelt.com> |
||||
Copyright (C) 2008-2013 Nathan Hjelm <hjelmn@users.sourceforge.net> |
||||
Copyright (C) 2009-2012 Pete Batard <pete@akeo.ie> |
||||
Copyright (C) 2010 Michael Plante <michael.plante@gmail.com> |
||||
Copyright (C) 2010-2012 Peter Stuge <peter@stuge.se> |
||||
Copyright (C) 2011-2012 Hans de Goede <hdegoede@redhat.com> |
||||
Copyright (C) 2012 Martin Pieuchot <mpi@openbsd.org> |
||||
Copyright © 2001 Johannes Erdfelt <johannes@erdfelt.com> |
||||
Copyright © 2007-2009 Daniel Drake <dsd@gentoo.org> |
||||
Copyright © 2010-2012 Peter Stuge <peter@stuge.se> |
||||
Copyright © 2008-2013 Nathan Hjelm <hjelmn@users.sourceforge.net> |
||||
Copyright © 2009-2013 Pete Batard <pete@akeo.ie> |
||||
Copyright © 2009-2013 Ludovic Rousseau <ludovic.rousseau@gmail.com> |
||||
Copyright © 2010-2012 Michael Plante <michael.plante@gmail.com> |
||||
Copyright © 2011-2013 Hans de Goede <hdegoede@redhat.com> |
||||
Copyright © 2012-2013 Martin Pieuchot <mpi@openbsd.org> |
||||
Copyright © 2012-2013 Toby Gray <toby.gray@realvnc.com> |
||||
|
||||
Other contributors: |
||||
Alan Ott |
||||
Alan Stern |
||||
Alex Vatchenko |
||||
Anthony Clay |
||||
Artem Egorkine |
||||
Aurelien Jarno |
||||
Bastien Nocera |
||||
Brian Shirley |
||||
Benjamin Dobell |
||||
Chris Dickens |
||||
Colin Walters |
||||
Dave Camarillo |
||||
David Engraf |
||||
David Moore |
||||
Davidlohr Bueso |
||||
Federico Manzan |
||||
Felipe Balbi |
||||
Florian Albrechtskirchinger |
||||
Francesco Montorsi |
||||
Graeme Gill |
||||
Hans de Goede |
||||
Hans Ulrich Niedermann |
||||
Hector Martin |
||||
Hoi-Ho Chan |
||||
Ilya Konstantinov |
||||
James Hanko |
||||
Konrad Rzepecki |
||||
Ludovic Rousseau |
||||
Lars Wirzenius |
||||
Luca Longinotti |
||||
Martin Koegler |
||||
Martin Pieuchot |
||||
Maya Erez |
||||
Matthias Bolte |
||||
Mike Frysinger |
||||
Mikhail Gusarov |
||||
Nicholas Corgan |
||||
Orin Eman |
||||
Paul Fertser |
||||
Pekka Nikander |
||||
Peter Stuge |
||||
Rob Walker |
||||
Sean McBride |
||||
Sebastian Pipping |
||||
Stephan Meyer |
||||
Simon Haggett |
||||
Thomas Röfer |
||||
Tim Roberts |
||||
Toby Peterson |
||||
Trygve Laugstøl |
||||
Uri Lublin |
||||
Vasily Khoruzhick |
||||
Vegard Storheil Eriksen |
||||
Vitali Lovich |
||||
Xiaofan Chen |
||||
Zoltán Kovács |
||||
Роман Донченко |
||||
|
@ -0,0 +1,196 @@
@@ -0,0 +1,196 @@
|
||||
For detailed information about the changes below, please see the git log or |
||||
visit: http://log.libusbx.org |
||||
|
||||
2013-09-06: v1.0.17 |
||||
* Hotplug callbacks now always get passed a libusb_context, even if it is |
||||
the default context. Previously NULL would be passed for the default context, |
||||
but since the first context created is the default context, and most apps |
||||
use only 1 context, this meant that apps explicitly creating a context would |
||||
still get passed NULL |
||||
* Android: Add .mk files to build with the Android NDK |
||||
* Darwin: Add Xcode project |
||||
* Darwin: Fix crash on unplug (#121) |
||||
* Linux: Fix hang (deadlock) on libusb_exit |
||||
* Linux: Fix libusbx build failure with --disable-udev (#124) |
||||
* Linux: Fix libusb_get_device_list() hang with --disable-udev (#130) |
||||
* OpenBSD: Update OpenBSD backend with support for control transfers to |
||||
non-ugen(4) devices and make get_configuration() no longer generate I/O. |
||||
Note that using this libusbx version on OpenBSD requires using |
||||
OpenBSD 5.3-current or later. Users of older OpenBSD versions are advised |
||||
to stay with the libusb shipped with OpenBSD (mpi) |
||||
* Windows: fix libusb_dll_2010.vcxproj link errors (#129) |
||||
* Various other bug fixes and improvements |
||||
The (#xx) numbers are libusbx issue numbers, see ie: |
||||
https://github.com/libusbx/libusbx/issues/121 |
||||
|
||||
2013-07-11: v1.0.16 |
||||
* Add hotplug support for Darwin and Linux (#9) |
||||
* Add superspeed endpoint companion descriptor support (#15) |
||||
* Add BOS descriptor support (#15) |
||||
* Make descriptor parsing code more robust |
||||
* New libusb_get_port_numbers API, this is libusb_get_port_path without |
||||
the unnecessary context parameter, libusb_get_port_path is now deprecated |
||||
* New libusb_strerror API (#14) |
||||
* New libusb_set_auto_detach_kernel_driver API (#17) |
||||
* Improve topology API docs (#95) |
||||
* Logging now use a single write call per log-message, avoiding log-message |
||||
"interlacing" when using multiple threads. |
||||
* Android: use Android logging when building on Android (#101) |
||||
* Darwin: make libusb_reset reenumerate device on descriptors change (#89) |
||||
* Darwin: add support for the LIBUSB_TRANSFER_ADD_ZERO_PACKET flag (#91) |
||||
* Darwin: add a device cache (#112, #114) |
||||
* Examples: Add sam3u_benchmark isochronous example by Harald Welte (#109) |
||||
* Many other bug fixes and improvements |
||||
The (#xx) numbers are libusbx issue numbers, see ie: |
||||
https://github.com/libusbx/libusbx/issues/9 |
||||
|
||||
2013-04-15: v1.0.15 |
||||
* Improve transfer cancellation and avoid short read failures on broken descriptors |
||||
* Filter out 8-bit characters in libusb_get_string_descriptor_ascii() |
||||
* Add WinCE support |
||||
* Add library stress tests |
||||
* Add Cypress FX3 firmware upload support for fxload sample |
||||
* Add HID and kernel driver detach support capabilities detection |
||||
* Add SuperSpeed detection on OS X |
||||
* Fix bInterval value interpretation on OS X |
||||
* Fix issues with autoclaim, composite HID devices, interface autoclaim and |
||||
early abort in libusb_close() on Windows. Also add VS2012 solution files. |
||||
* Improve fd event handling on Linux |
||||
* Other bug fixes and improvements |
||||
|
||||
2012-09-26: v1.0.14 |
||||
* Reverts the previous API change with regards to bMaxPower. |
||||
If this doesn't matter to you, you are encouraged to keep using v1.0.13, |
||||
as it will use the same attribute as v2.0, to be released soon. |
||||
* Note that LIBUSBX_API_VERSION is *decreased* to 0x010000FF and the previous |
||||
guidelines with regards to concurrent use of MaxPower/bMaxPower still apply. |
||||
|
||||
2012-09-20: v1.0.13 |
||||
* [MAJOR] Fix a typo in the API with struct libusb_config_descriptor where |
||||
MaxPower was used instead of bMaxPower, as defined in the specs. If your |
||||
application was accessing the MaxPower attribute, and you need to maintain |
||||
compatibility with libusb or older versions, see APPENDIX A below. |
||||
* Fix broken support for the 0.1 -> 1.0 libusb-compat layer |
||||
* Fix unwanted cancellation of pending timeouts as well as major timeout related bugs |
||||
* Fix handling of HID and composite devices on Windows |
||||
* Introduce LIBUSBX_API_VERSION macro |
||||
* Add Cypress FX/FX2 firmware upload sample, based on fxload from |
||||
http://linux-hotplug.sourceforge.net |
||||
* Add libusb0 (libusb-win32) and libusbK driver support on Windows. Note that while |
||||
the drivers allow it, isochronous transfers are not supported yet in libusbx. Also |
||||
not supported yet is the use of libusb-win32 filter drivers on composite interfaces |
||||
* Add support for the new get_capabilities ioctl on Linux and avoid unnecessary |
||||
splitting of bulk transfers |
||||
* Improve support for newer Intel and Renesas USB 3.0 controllers on Windows |
||||
* Harmonize the device number for root hubs across platforms |
||||
* Other bug fixes and improvements |
||||
|
||||
2012-06-15: v1.0.12 |
||||
* Fix a potential major regression with pthread on Linux |
||||
* Fix missing thread ID from debug log output on cygwin |
||||
* Fix possible crash when using longjmp and MinGW's gcc 4.6 |
||||
* Add topology calls: libusb_get_port_number(), libusb_get_parent() & libusb_get_port_path() |
||||
* Add toggleable debug, using libusb_set_debug() or the LIBUSB_DEBUG environment variable |
||||
* Define log levels in libusb.h and set timestamp origin to first libusb_init() call |
||||
* All logging is now sent to to stderr (info was sent to stdout previously) |
||||
* Update log messages severity and avoid polluting log output on OS-X |
||||
* Add HID driver support on Windows |
||||
* Enable interchangeability of MSVC and MinGW DLLs |
||||
* Additional bug fixes and improvements |
||||
|
||||
2012-05-08: v1.0.11 |
||||
* Revert removal of critical Windows event handling that was introduced in 1.0.10 |
||||
* Fix a possible deadlock in Windows when submitting transfers |
||||
* Add timestamped logging |
||||
* Add NetBSD support (experimental) and BSD libusb_get_device_speed() data |
||||
* Add bootstrap.sh alongside autogen.sh (bootstrap.sh doesn't invoke configure) |
||||
* Search for device nodes in /dev for Android support |
||||
* Other bug fixes |
||||
|
||||
2012-04-17: v1.0.10 |
||||
* Public release |
||||
* Add libusb_get_version |
||||
* Add Visual Studio 2010 project files |
||||
* Some Windows code cleanup |
||||
* Fix xusb sample warnings |
||||
|
||||
2012-04-02: v1.0.9 |
||||
* First libusbx release |
||||
* Add libusb_get_device_speed (all, except BSD) and libusb_error_name |
||||
* Add Windows support (WinUSB driver only) |
||||
* Add OpenBSD support |
||||
* Add xusb sample |
||||
* Tons of bug fixes |
||||
|
||||
2010-05-07: v1.0.8 |
||||
* Bug fixes |
||||
|
||||
2010-04-19: v1.0.7 |
||||
* Bug fixes and documentation tweaks |
||||
* Add more interface class definitions |
||||
|
||||
2009-11-22: v1.0.6 |
||||
* Bug fixes |
||||
* Increase libusb_handle_events() timeout to 60s for powersaving |
||||
|
||||
2009-11-15: v1.0.5 |
||||
* Use timerfd when available for timer management |
||||
* Small fixes/updates |
||||
|
||||
2009-11-06: v1.0.4 release |
||||
* Bug fixes including transfer locking to fix some potential threading races |
||||
* More flexibility with clock types on Linux |
||||
* Use new bulk continuation tracking in Linux 2.6.32 for improved handling |
||||
of short/failed transfers |
||||
|
||||
2009-08-27: v1.0.3 release |
||||
* Bug fixes |
||||
* Add libusb_get_max_iso_packet_size() |
||||
|
||||
2009-06-13: v1.0.2 release |
||||
* Bug fixes |
||||
|
||||
2009-05-12: v1.0.1 release |
||||
* Bug fixes |
||||
* Darwin backend |
||||
|
||||
2008-12-13: v1.0.0 release |
||||
* Bug fixes |
||||
|
||||
2008-11-21: v0.9.4 release |
||||
* Bug fixes |
||||
* Add libusb_attach_kernel_driver() |
||||
|
||||
2008-08-23: v0.9.3 release |
||||
* Bug fixes |
||||
|
||||
2008-07-19: v0.9.2 release |
||||
* Bug fixes |
||||
|
||||
2008-06-28: v0.9.1 release |
||||
* Bug fixes |
||||
* Introduce contexts to the API |
||||
* Compatibility with new Linux kernel features |
||||
|
||||
2008-05-25: v0.9.0 release |
||||
* First libusb-1.0 beta release |
||||
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
||||
|
||||
APPENDIX A - How to maintain code compatibility with versions of libusb and |
||||
libusbx that use MaxPower: |
||||
|
||||
If you must to maintain compatibility with versions of the library that aren't |
||||
using the bMaxPower attribute in struct libusb_config_descriptor, the |
||||
recommended way is to use the new LIBUSBX_API_VERSION macro with an #ifdef. |
||||
For instance, if your code was written as follows: |
||||
|
||||
if (dev->config[0].MaxPower < 250) |
||||
|
||||
Then you should modify it to have: |
||||
|
||||
#if defined(LIBUSBX_API_VERSION) && (LIBUSBX_API_VERSION >= 0x01000100) |
||||
if (dev->config[0].bMaxPower < 250) |
||||
#else |
||||
if (dev->config[0].MaxPower < 250) |
||||
#endif |
@ -1,65 +1,2 @@
@@ -1,65 +1,2 @@
|
||||
This file lists notable changes in each release. For the full history of all |
||||
changes, see ChangeLog. |
||||
|
||||
2012-04-20: 1.0.9 |
||||
* Numerous bug fixes and improvements |
||||
* Backend for Windows, for devices using the WinUSB.sys driver |
||||
* Backend for OpenBSD and NetBSD, for devices using the ugen driver |
||||
* Add libusb_get_device_speed() |
||||
* Add libusb_has_capability() |
||||
* Add libusb_error_name() |
||||
* Add libusb_get_version() |
||||
|
||||
2010-05-07: v1.0.8 |
||||
* Bug fixes |
||||
|
||||
2010-04-19: v1.0.7 |
||||
* Bug fixes and documentation tweaks |
||||
* Add more interface class definitions |
||||
|
||||
2009-11-22: v1.0.6 |
||||
* Bug fixes |
||||
* Increase libusb_handle_events() timeout to 60s for powersaving |
||||
|
||||
2009-11-15: v1.0.5 |
||||
* Use timerfd when available for timer management |
||||
* Small fixes/updates |
||||
|
||||
2009-11-06: v1.0.4 release |
||||
* Bug fixes including transfer locking to fix some potential threading races |
||||
* More flexibility with clock types on Linux |
||||
* Use new bulk continuation tracking in Linux 2.6.32 for improved handling |
||||
of short/failed transfers |
||||
|
||||
2009-08-27: v1.0.3 release |
||||
* Bug fixes |
||||
* Add libusb_get_max_iso_packet_size() |
||||
|
||||
2009-06-13: v1.0.2 release |
||||
* Bug fixes |
||||
|
||||
2009-05-12: v1.0.1 release |
||||
* Bug fixes |
||||
* Darwin backend |
||||
|
||||
2008-12-13: v1.0.0 release |
||||
* Bug fixes |
||||
|
||||
2008-11-21: v0.9.4 release |
||||
* Bug fixes |
||||
* Add libusb_attach_kernel_driver() |
||||
|
||||
2008-08-23: v0.9.3 release |
||||
* Bug fixes |
||||
|
||||
2008-07-19: v0.9.2 release |
||||
* Bug fixes |
||||
|
||||
2008-06-28: v0.9.1 release |
||||
* Bug fixes |
||||
* Introduce contexts to the API |
||||
* Compatibility with new Linux kernel features |
||||
|
||||
2008-05-25: v0.9.0 release |
||||
* First libusb-1.0 beta release |
||||
|
||||
For the latest libusbx news, please refer to the ChangeLog file, or visit: |
||||
http://libusbx.org |
||||
|
@ -1,22 +1,29 @@
@@ -1,22 +1,29 @@
|
||||
libusb |
||||
====== |
||||
libusbx |
||||
======= |
||||
|
||||
libusb is a library for USB device access from Linux, Mac OS X, |
||||
OpenBSD, NetBSD, and Windows userspace. |
||||
It is written in C and licensed under the LGPL-2.1 (see COPYING). |
||||
libusbx is a library for USB device access from Linux, Mac OS X, |
||||
Windows and OpenBSD/NetBSD userspace, with OpenBSD/NetBSD, and to a |
||||
lesser extent some of the newest features of Windows (such as libusbK |
||||
and libusb-win32 driver support) being EXPERIMENTAL. |
||||
It is written in C and licensed under the GNU Lesser General Public |
||||
License version 2.1 or, at your option, any later version (see COPYING). |
||||
|
||||
libusb is abstracted internally in such a way that it can hopefully |
||||
be ported to other operating systems. See the PORTING file for some |
||||
information, if you fancy a challenge. :) |
||||
libusbx is abstracted internally in such a way that it can hopefully |
||||
be ported to other operating systems. Please see the PORTING file |
||||
for more information. |
||||
|
||||
libusb homepage: |
||||
http://libusb.org/ |
||||
libusbx homepage: |
||||
http://libusbx.org/ |
||||
|
||||
Developers will wish to consult the API documentation: |
||||
http://libusb.sourceforge.net/api-1.0/ |
||||
http://api.libusbx.org |
||||
|
||||
Use the mailing list for questions, comments, etc: |
||||
http://libusb.org/wiki/MailingList |
||||
http://mailing-list.libusbx.org |
||||
|
||||
- Peter Stuge <peter@stuge.se> |
||||
(use the mailing list rather than mailing developers directly) |
||||
- Pete Batard <pete@akeo.ie> |
||||
- Hans de Goede <hdegoede@redhat.com> |
||||
- Xiaofan Chen <xiaofanc@gmail.com> |
||||
- Ludovic Rousseau <ludovic.rousseau@gmail.com> |
||||
- Nathan Hjelm <hjelmn@users.sourceforge.net> |
||||
(Please use the mailing list rather than mailing developers directly) |
||||
|
@ -1,8 +0,0 @@
@@ -1,8 +0,0 @@
|
||||
Development contributors are listed in the AUTHORS file. Other community |
||||
members who have made significant contributions in other areas are listed |
||||
in this file: |
||||
|
||||
Alan Stern |
||||
Ludovic Rousseau |
||||
Tim Roberts |
||||
Xiaofan Chen |
@ -1,9 +1,2 @@
@@ -1,9 +1,2 @@
|
||||
for 1.1 or future |
||||
================== |
||||
optional timerfd support (runtime detection) |
||||
notifications of hotplugged/unplugged devices |
||||
offer API to create/destroy handle_events thread |
||||
isochronous sync I/O? |
||||
exposing of parent-child device relationships |
||||
"usb primer" introduction docs |
||||
more examples |
||||
Please see the libusbx roadmap by visiting: |
||||
https://github.com/libusbx/libusbx/issues/milestones?direction=asc&sort=due_date |
@ -1,256 +0,0 @@
@@ -1,256 +0,0 @@
|
||||
/*
|
||||
* Test suite program based of libusb-0.1-compat testlibusb |
||||
* Copyright (c) 2013 Nathan Hjelm <hjelmn@mac.ccom> |
||||
* |
||||
* This library is free software; you can redistribute it and/or |
||||
* modify it under the terms of the GNU Lesser General Public |
||||
* License as published by the Free Software Foundation; either |
||||
* version 2.1 of the License, or (at your option) any later version. |
||||
* |
||||
* This library is distributed in the hope that it will be useful, |
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
||||
* Lesser General Public License for more details. |
||||
* |
||||
* You should have received a copy of the GNU Lesser General Public |
||||
* License along with this library; if not, write to the Free Software |
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
||||
*/ |
||||
|
||||
#include <stdio.h> |
||||
#include <string.h> |
||||
#include <libusb.h> |
||||
|
||||
int verbose = 0; |
||||
|
||||
static void print_endpoint_comp(const struct libusb_ss_endpoint_companion_descriptor *ep_comp) |
||||
{ |
||||
printf(" USB 3.0 Endpoint Companion:\n"); |
||||
printf(" bMaxBurst: %d\n", ep_comp->bMaxBurst); |
||||
printf(" bmAttributes: 0x%02x\n", ep_comp->bmAttributes); |
||||
printf(" wBytesPerInterval: %d\n", ep_comp->wBytesPerInterval); |
||||
} |
||||
|
||||
static void print_endpoint(const struct libusb_endpoint_descriptor *endpoint) |
||||
{ |
||||
int i, ret; |
||||
|
||||
printf(" Endpoint:\n"); |
||||
printf(" bEndpointAddress: %02xh\n", endpoint->bEndpointAddress); |
||||
printf(" bmAttributes: %02xh\n", endpoint->bmAttributes); |
||||
printf(" wMaxPacketSize: %d\n", endpoint->wMaxPacketSize); |
||||
printf(" bInterval: %d\n", endpoint->bInterval); |
||||
printf(" bRefresh: %d\n", endpoint->bRefresh); |
||||
printf(" bSynchAddress: %d\n", endpoint->bSynchAddress); |
||||
|
||||
for (i = 0 ; i < endpoint->extra_length ; ) { |
||||
if (LIBUSB_DT_SS_ENDPOINT_COMPANION == endpoint->extra[i+1]) { |
||||
struct libusb_ss_endpoint_companion_descriptor *ep_comp; |
||||
|
||||
ret = libusb_parse_ss_endpoint_comp(endpoint->extra+i, endpoint->extra[0], &ep_comp); |
||||
if (LIBUSB_SUCCESS != ret) { |
||||
continue; |
||||
} |
||||
|
||||
print_endpoint_comp(ep_comp); |
||||
|
||||
libusb_free_ss_endpoint_comp(ep_comp); |
||||
} |
||||
|
||||
i += endpoint->extra[i]; |
||||
} |
||||
} |
||||
|
||||
static void print_altsetting(const struct libusb_interface_descriptor *interface) |
||||
{ |
||||
int i; |
||||
|
||||
printf(" Interface:\n"); |
||||
printf(" bInterfaceNumber: %d\n", interface->bInterfaceNumber); |
||||
printf(" bAlternateSetting: %d\n", interface->bAlternateSetting); |
||||
printf(" bNumEndpoints: %d\n", interface->bNumEndpoints); |
||||
printf(" bInterfaceClass: %d\n", interface->bInterfaceClass); |
||||
printf(" bInterfaceSubClass: %d\n", interface->bInterfaceSubClass); |
||||
printf(" bInterfaceProtocol: %d\n", interface->bInterfaceProtocol); |
||||
printf(" iInterface: %d\n", interface->iInterface); |
||||
|
||||
for (i = 0; i < interface->bNumEndpoints; i++) |
||||
print_endpoint(&interface->endpoint[i]); |
||||
} |
||||
|
||||
static void print_2_0_ext_cap(struct libusb_usb_2_0_device_capability_descriptor *usb_2_0_ext_cap) |
||||
{ |
||||
printf(" USB 2.0 Extension Capabilities:\n"); |
||||
printf(" bDevCapabilityType: %d\n", usb_2_0_ext_cap->bDevCapabilityType); |
||||
printf(" bmAttributes: 0x%x\n", usb_2_0_ext_cap->bmAttributes); |
||||
} |
||||
|
||||
static void print_ss_usb_cap(struct libusb_ss_usb_device_capability_descriptor *ss_usb_cap) |
||||
{ |
||||
printf(" USB 3.0 Capabilities:\n"); |
||||
printf(" bDevCapabilityType: %d\n", ss_usb_cap->bDevCapabilityType); |
||||
printf(" bmAttributes: 0x%x\n", ss_usb_cap->bmAttributes); |
||||
printf(" wSpeedSupported: 0x%x\n", ss_usb_cap->wSpeedSupported); |
||||
printf(" bFunctionalitySupport: %d\n", ss_usb_cap->bFunctionalitySupport); |
||||
printf(" bU1devExitLat: %d\n", ss_usb_cap->bU1DevExitLat); |
||||
printf(" bU2devExitLat: %d\n", ss_usb_cap->bU2DevExitLat); |
||||
} |
||||
|
||||
static void print_bos(libusb_device_handle *handle) |
||||
{ |
||||
unsigned char buffer[128]; |
||||
struct libusb_bos_descriptor *bos; |
||||
int ret; |
||||
|
||||
ret = libusb_get_descriptor(handle, LIBUSB_DT_BOS, 0, buffer, 128); |
||||
if (0 > ret) { |
||||
return; |
||||
} |
||||
|
||||
ret = libusb_parse_bos_descriptor(buffer, 128, &bos); |
||||
if (0 > ret) { |
||||
return; |
||||
} |
||||
|
||||
printf(" Binary Object Store (BOS):\n"); |
||||
printf(" wTotalLength: %d\n", bos->wTotalLength); |
||||
printf(" bNumDeviceCaps: %d\n", bos->bNumDeviceCaps); |
||||
if (bos->usb_2_0_ext_cap) { |
||||
print_2_0_ext_cap(bos->usb_2_0_ext_cap); |
||||
} |
||||
|
||||
if (bos->ss_usb_cap) { |
||||
print_ss_usb_cap(bos->ss_usb_cap); |
||||
} |
||||
} |
||||
|
||||
static void print_interface(const struct libusb_interface *interface) |
||||
{ |
||||
int i; |
||||
|
||||
for (i = 0; i < interface->num_altsetting; i++) |
||||
print_altsetting(&interface->altsetting[i]); |
||||
} |
||||
|
||||
static void print_configuration(struct libusb_config_descriptor *config) |
||||
{ |
||||
int i; |
||||
|
||||
printf(" Configuration:\n"); |
||||
printf(" wTotalLength: %d\n", config->wTotalLength); |
||||
printf(" bNumInterfaces: %d\n", config->bNumInterfaces); |
||||
printf(" bConfigurationValue: %d\n", config->bConfigurationValue); |
||||
printf(" iConfiguration: %d\n", config->iConfiguration); |
||||
printf(" bmAttributes: %02xh\n", config->bmAttributes); |
||||
printf(" MaxPower: %d\n", config->MaxPower); |
||||
|
||||
for (i = 0; i < config->bNumInterfaces; i++) |
||||
print_interface(&config->interface[i]); |
||||
} |
||||
|
||||
static int print_device(libusb_device *dev, int level) |
||||
{ |
||||
struct libusb_device_descriptor desc; |
||||
libusb_device_handle *handle = NULL; |
||||
char description[256]; |
||||
char string[256]; |
||||
int ret, i; |
||||
|
||||
ret = libusb_get_device_descriptor(dev, &desc); |
||||
if (ret < 0) { |
||||
fprintf(stderr, "failed to get device descriptor"); |
||||
return -1; |
||||
} |
||||
|
||||
ret = libusb_open(dev, &handle); |
||||
if (LIBUSB_SUCCESS == ret) { |
||||
if (desc.iManufacturer) { |
||||
ret = libusb_get_string_descriptor_ascii(handle, desc.iManufacturer, string, sizeof(string)); |
||||
if (ret > 0) |
||||
snprintf(description, sizeof(description), "%s - ", string); |
||||
else |
||||
snprintf(description, sizeof(description), "%04X - ", |
||||
desc.idVendor); |
||||
} else |
||||
snprintf(description, sizeof(description), "%04X - ", |
||||
desc.idVendor); |
||||
|
||||
if (desc.iProduct) { |
||||
ret = libusb_get_string_descriptor_ascii(handle, desc.iProduct, string, sizeof(string)); |
||||
if (ret > 0) |
||||
snprintf(description + strlen(description), sizeof(description) - |
||||
strlen(description), "%s", string); |
||||
else |
||||
snprintf(description + strlen(description), sizeof(description) - |
||||
strlen(description), "%04X", desc.idProduct); |
||||
} else |
||||
snprintf(description + strlen(description), sizeof(description) - |
||||
strlen(description), "%04X", desc.idProduct); |
||||
} else { |
||||
snprintf(description, sizeof(description), "%04X - %04X", |
||||
desc.idVendor, desc.idProduct); |
||||
} |
||||
|
||||
printf("%.*sDev (bus %d, device %d): %s\n", level * 2, " ", |
||||
libusb_get_bus_number(dev), libusb_get_device_address(dev), description); |
||||
|
||||
if (handle && verbose) { |
||||
if (desc.iSerialNumber) { |
||||
ret = libusb_get_string_descriptor_ascii(handle, desc.iSerialNumber, string, sizeof(string)); |
||||
if (ret > 0) |
||||
printf("%.*s - Serial Number: %s\n", level * 2, |
||||
" ", string); |
||||
} |
||||
} |
||||
|
||||
if (verbose) { |
||||
for (i = 0; i < desc.bNumConfigurations; i++) { |
||||
struct libusb_config_descriptor *config; |
||||
ret = libusb_get_config_descriptor(dev, i, &config); |
||||
if (LIBUSB_SUCCESS != ret) { |
||||
printf(" Couldn't retrieve descriptors\n"); |
||||
continue; |
||||
} |
||||
|
||||
print_configuration(config); |
||||
|
||||
libusb_free_config_descriptor(config); |
||||
} |
||||
|
||||
if (handle && desc.bcdUSB >= 0x0201) { |
||||
print_bos(handle); |
||||
} |
||||
} |
||||
|
||||
if (handle) |
||||
libusb_close(handle); |
||||
|
||||
return 0; |
||||
} |
||||
|
||||
int main(int argc, char *argv[]) |
||||
{ |
||||
libusb_device **devs; |
||||
ssize_t cnt; |
||||
int r, i; |
||||
|
||||
if (argc > 1 && !strcmp(argv[1], "-v")) |
||||
verbose = 1; |
||||
|
||||
r = libusb_init(NULL); |
||||
if (r < 0) |
||||
return r; |
||||
|
||||
cnt = libusb_get_device_list(NULL, &devs); |
||||
if (cnt < 0) |
||||
return (int) cnt; |
||||
|
||||
for (i = 0 ; devs[i] ; ++i) { |
||||
print_device(devs[i], 0); |
||||
} |
||||
|
||||
libusb_free_device_list(devs, 1); |
||||
|
||||
libusb_exit(NULL); |
||||
return 0; |
||||
} |
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,734 @@
@@ -0,0 +1,734 @@
|
||||
/*
|
||||
* Copyright © 2011 Martin Pieuchot <mpi@openbsd.org> |
||||
* |
||||
* This library is free software; you can redistribute it and/or |
||||
* modify it under the terms of the GNU Lesser General Public |
||||
* License as published by the Free Software Foundation; either |
||||
* version 2.1 of the License, or (at your option) any later version. |
||||
* |
||||
* This library is distributed in the hope that it will be useful, |
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
||||
* Lesser General Public License for more details. |
||||
* |
||||
* You should have received a copy of the GNU Lesser General Public |
||||
* License along with this library; if not, write to the Free Software |
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
||||
*/ |
||||
|
||||
#include <sys/time.h> |
||||
#include <sys/types.h> |
||||
|
||||
#include <errno.h> |
||||
#include <fcntl.h> |
||||
#include <stdio.h> |
||||
#include <stdlib.h> |
||||
#include <string.h> |
||||
#include <unistd.h> |
||||
|
||||
#include <dev/usb/usb.h> |
||||
|
||||
#include "libusb.h" |
||||
#include "libusbi.h" |
||||
|
||||
struct device_priv { |
||||
char devnode[16]; |
||||
int fd; |
||||
|
||||
unsigned char *cdesc; /* active config descriptor */ |
||||
usb_device_descriptor_t ddesc; /* usb device descriptor */ |
||||
}; |
||||
|
||||
struct handle_priv { |
||||
int pipe[2]; /* for event notification */ |
||||
int endpoints[USB_MAX_ENDPOINTS]; |
||||
}; |
||||
|
||||
/*
|
||||
* Backend functions |
||||
*/ |
||||
static int netbsd_get_device_list(struct libusb_context *, |
||||
struct discovered_devs **); |
||||
static int netbsd_open(struct libusb_device_handle *); |
||||
static void netbsd_close(struct libusb_device_handle *); |
||||
|
||||
static int netbsd_get_device_descriptor(struct libusb_device *, unsigned char *, |
||||
int *); |
||||
static int netbsd_get_active_config_descriptor(struct libusb_device *, |
||||
unsigned char *, size_t, int *); |
||||
static int netbsd_get_config_descriptor(struct libusb_device *, uint8_t, |
||||
unsigned char *, size_t, int *); |
||||
|
||||
static int netbsd_get_configuration(struct libusb_device_handle *, int *); |
||||
static int netbsd_set_configuration(struct libusb_device_handle *, int); |
||||
|
||||
static int netbsd_claim_interface(struct libusb_device_handle *, int); |
||||
static int netbsd_release_interface(struct libusb_device_handle *, int); |
||||
|
||||
static int netbsd_set_interface_altsetting(struct libusb_device_handle *, int, |
||||
int); |
||||
static int netbsd_clear_halt(struct libusb_device_handle *, unsigned char); |
||||
static int netbsd_reset_device(struct libusb_device_handle *); |
||||
static void netbsd_destroy_device(struct libusb_device *); |
||||
|
||||
static int netbsd_submit_transfer(struct usbi_transfer *); |
||||
static int netbsd_cancel_transfer(struct usbi_transfer *); |
||||
static void netbsd_clear_transfer_priv(struct usbi_transfer *); |
||||
static int netbsd_handle_events(struct libusb_context *ctx, struct pollfd *, |
||||
nfds_t, int); |
||||
static int netbsd_clock_gettime(int, struct timespec *); |
||||
|
||||
/*
|
||||
* Private functions |
||||
*/ |
||||
static int _errno_to_libusb(int); |
||||
static int _cache_active_config_descriptor(struct libusb_device *, int); |
||||
static int _sync_control_transfer(struct usbi_transfer *); |
||||
static int _sync_gen_transfer(struct usbi_transfer *); |
||||
static int _access_endpoint(struct libusb_transfer *); |
||||
|
||||
const struct usbi_os_backend netbsd_backend = { |
||||
"Synchronous NetBSD backend", |
||||
0, |
||||
NULL, /* init() */ |
||||
NULL, /* exit() */ |
||||
netbsd_get_device_list, |
||||
NULL, /* hotplug_poll */ |
||||
netbsd_open, |
||||
netbsd_close, |
||||
|
||||
netbsd_get_device_descriptor, |
||||
netbsd_get_active_config_descriptor, |
||||
netbsd_get_config_descriptor, |
||||
NULL, /* get_config_descriptor_by_value() */ |
||||
|
||||
netbsd_get_configuration, |
||||
netbsd_set_configuration, |
||||
|
||||
netbsd_claim_interface, |
||||
netbsd_release_interface, |
||||
|
||||
netbsd_set_interface_altsetting, |
||||
netbsd_clear_halt, |
||||
netbsd_reset_device, |
||||
|
||||
NULL, /* kernel_driver_active() */ |
||||
NULL, /* detach_kernel_driver() */ |
||||
NULL, /* attach_kernel_driver() */ |
||||
|
||||
netbsd_destroy_device, |
||||
|
||||
netbsd_submit_transfer, |
||||
netbsd_cancel_transfer, |
||||
netbsd_clear_transfer_priv, |
||||
|
||||
netbsd_handle_events, |
||||
|
||||
netbsd_clock_gettime, |
||||
sizeof(struct device_priv), |
||||
sizeof(struct handle_priv), |
||||
0, /* transfer_priv_size */ |
||||
0, /* add_iso_packet_size */ |
||||
}; |
||||
|
||||
int |
||||
netbsd_get_device_list(struct libusb_context * ctx, |
||||
struct discovered_devs **discdevs) |
||||
{ |
||||
struct libusb_device *dev; |
||||
struct device_priv *dpriv; |
||||
struct usb_device_info di; |
||||
unsigned long session_id; |
||||
char devnode[16]; |
||||
int fd, err, i; |
||||
|
||||
usbi_dbg(""); |
||||
|
||||
/* Only ugen(4) is supported */ |
||||
for (i = 0; i < USB_MAX_DEVICES; i++) { |
||||
/* Control endpoint is always .00 */ |
||||
snprintf(devnode, sizeof(devnode), "/dev/ugen%d.00", i); |
||||
|
||||
if ((fd = open(devnode, O_RDONLY)) < 0) { |
||||
if (errno != ENOENT && errno != ENXIO) |
||||
usbi_err(ctx, "could not open %s", devnode); |
||||
continue; |
||||
} |
||||
|
||||
if (ioctl(fd, USB_GET_DEVICEINFO, &di) < 0) |
||||
continue; |
||||
|
||||
session_id = (di.udi_bus << 8 | di.udi_addr); |
||||
dev = usbi_get_device_by_session_id(ctx, session_id); |
||||
|
||||
if (dev) { |
||||
dev = libusb_ref_device(dev); |
||||
} else { |
||||
dev = usbi_alloc_device(ctx, session_id); |
||||
if (dev == NULL) |
||||
return (LIBUSB_ERROR_NO_MEM); |
||||
|
||||
dev->bus_number = di.udi_bus; |
||||
dev->device_address = di.udi_addr; |
||||
dev->speed = di.udi_speed; |
||||
|
||||
dpriv = (struct device_priv *)dev->os_priv; |
||||
strlcpy(dpriv->devnode, devnode, sizeof(devnode)); |
||||
dpriv->fd = -1; |
||||
|
||||
if (ioctl(fd, USB_GET_DEVICE_DESC, &dpriv->ddesc) < 0) { |
||||
err = errno; |
||||
goto error; |
||||
} |
||||
|
||||
dpriv->cdesc = NULL; |
||||
if (_cache_active_config_descriptor(dev, fd)) { |
||||
err = errno; |
||||
goto error; |
||||
} |
||||
|
||||
if ((err = usbi_sanitize_device(dev))) |
||||
goto error; |
||||
} |
||||
close(fd); |
||||
|
||||
if (discovered_devs_append(*discdevs, dev) == NULL) |
||||
return (LIBUSB_ERROR_NO_MEM); |
||||
|
||||
libusb_unref_device(dev); |
||||
} |
||||
|
||||
return (LIBUSB_SUCCESS); |
||||
|
||||
error: |
||||
close(fd); |
||||
libusb_unref_device(dev); |
||||
return _errno_to_libusb(err); |
||||
} |
||||
|
||||
int |
||||
netbsd_open(struct libusb_device_handle *handle) |
||||
{ |
||||
struct handle_priv *hpriv = (struct handle_priv *)handle->os_priv; |
||||
struct device_priv *dpriv = (struct device_priv *)handle->dev->os_priv; |
||||
|
||||
dpriv->fd = open(dpriv->devnode, O_RDWR); |
||||
if (dpriv->fd < 0) { |
||||
dpriv->fd = open(dpriv->devnode, O_RDONLY); |
||||
if (dpriv->fd < 0) |
||||
return _errno_to_libusb(errno); |
||||
} |
||||
|
||||
usbi_dbg("open %s: fd %d", dpriv->devnode, dpriv->fd); |
||||
|
||||
if (pipe(hpriv->pipe) < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
return usbi_add_pollfd(HANDLE_CTX(handle), hpriv->pipe[0], POLLIN); |
||||
} |
||||
|
||||
void |
||||
netbsd_close(struct libusb_device_handle *handle) |
||||
{ |
||||
struct handle_priv *hpriv = (struct handle_priv *)handle->os_priv; |
||||
struct device_priv *dpriv = (struct device_priv *)handle->dev->os_priv; |
||||
|
||||
usbi_dbg("close: fd %d", dpriv->fd); |
||||
|
||||
close(dpriv->fd); |
||||
dpriv->fd = -1; |
||||
|
||||
usbi_remove_pollfd(HANDLE_CTX(handle), hpriv->pipe[0]); |
||||
|
||||
close(hpriv->pipe[0]); |
||||
close(hpriv->pipe[1]); |
||||
} |
||||
|
||||
int |
||||
netbsd_get_device_descriptor(struct libusb_device *dev, unsigned char *buf, |
||||
int *host_endian) |
||||
{ |
||||
struct device_priv *dpriv = (struct device_priv *)dev->os_priv; |
||||
|
||||
usbi_dbg(""); |
||||
|
||||
memcpy(buf, &dpriv->ddesc, DEVICE_DESC_LENGTH); |
||||
|
||||
*host_endian = 0; |
||||
|
||||
return (LIBUSB_SUCCESS); |
||||
} |
||||
|
||||
int |
||||
netbsd_get_active_config_descriptor(struct libusb_device *dev, |
||||
unsigned char *buf, size_t len, int *host_endian) |
||||
{ |
||||
struct device_priv *dpriv = (struct device_priv *)dev->os_priv; |
||||
usb_config_descriptor_t *ucd; |
||||
|
||||
ucd = (usb_config_descriptor_t *) dpriv->cdesc; |
||||
len = MIN(len, UGETW(ucd->wTotalLength)); |
||||
|
||||
usbi_dbg("len %d", len); |
||||
|
||||
memcpy(buf, dpriv->cdesc, len); |
||||
|
||||
*host_endian = 0; |
||||
|
||||
return len; |
||||
} |
||||
|
||||
int |
||||
netbsd_get_config_descriptor(struct libusb_device *dev, uint8_t idx, |
||||
unsigned char *buf, size_t len, int *host_endian) |
||||
{ |
||||
struct device_priv *dpriv = (struct device_priv *)dev->os_priv; |
||||
struct usb_full_desc ufd; |
||||
int fd, err; |
||||
|
||||
usbi_dbg("index %d, len %d", idx, len); |
||||
|
||||
/* A config descriptor may be requested before opening the device */ |
||||
if (dpriv->fd >= 0) { |
||||
fd = dpriv->fd; |
||||
} else { |
||||
fd = open(dpriv->devnode, O_RDONLY); |
||||
if (fd < 0) |
||||
return _errno_to_libusb(errno); |
||||
} |
||||
|
||||
ufd.ufd_config_index = idx; |
||||
ufd.ufd_size = len; |
||||
ufd.ufd_data = buf; |
||||
|
||||
if ((ioctl(fd, USB_GET_FULL_DESC, &ufd)) < 0) { |
||||
err = errno; |
||||
if (dpriv->fd < 0) |
||||
close(fd); |
||||
return _errno_to_libusb(err); |
||||
} |
||||
|
||||
if (dpriv->fd < 0) |
||||
close(fd); |
||||
|
||||
*host_endian = 0; |
||||
|
||||
return len; |
||||
} |
||||
|
||||
int |
||||
netbsd_get_configuration(struct libusb_device_handle *handle, int *config) |
||||
{ |
||||
struct device_priv *dpriv = (struct device_priv *)handle->dev->os_priv; |
||||
|
||||
usbi_dbg(""); |
||||
|
||||
if (ioctl(dpriv->fd, USB_GET_CONFIG, config) < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
usbi_dbg("configuration %d", *config); |
||||
|
||||
return (LIBUSB_SUCCESS); |
||||
} |
||||
|
||||
int |
||||
netbsd_set_configuration(struct libusb_device_handle *handle, int config) |
||||
{ |
||||
struct device_priv *dpriv = (struct device_priv *)handle->dev->os_priv; |
||||
|
||||
usbi_dbg("configuration %d", config); |
||||
|
||||
if (ioctl(dpriv->fd, USB_SET_CONFIG, &config) < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
return _cache_active_config_descriptor(handle->dev, dpriv->fd); |
||||
} |
||||
|
||||
int |
||||
netbsd_claim_interface(struct libusb_device_handle *handle, int iface) |
||||
{ |
||||
struct handle_priv *hpriv = (struct handle_priv *)handle->os_priv; |
||||
int i; |
||||
|
||||
for (i = 0; i < USB_MAX_ENDPOINTS; i++) |
||||
hpriv->endpoints[i] = -1; |
||||
|
||||
return (LIBUSB_SUCCESS); |
||||
} |
||||
|
||||
int |
||||
netbsd_release_interface(struct libusb_device_handle *handle, int iface) |
||||
{ |
||||
struct handle_priv *hpriv = (struct handle_priv *)handle->os_priv; |
||||
int i; |
||||
|
||||
for (i = 0; i < USB_MAX_ENDPOINTS; i++) |
||||
if (hpriv->endpoints[i] >= 0) |
||||
close(hpriv->endpoints[i]); |
||||
|
||||
return (LIBUSB_SUCCESS); |
||||
} |
||||
|
||||
int |
||||
netbsd_set_interface_altsetting(struct libusb_device_handle *handle, int iface, |
||||
int altsetting) |
||||
{ |
||||
struct device_priv *dpriv = (struct device_priv *)handle->dev->os_priv; |
||||
struct usb_alt_interface intf; |
||||
|
||||
usbi_dbg("iface %d, setting %d", iface, altsetting); |
||||
|
||||
memset(&intf, 0, sizeof(intf)); |
||||
|
||||
intf.uai_interface_index = iface; |
||||
intf.uai_alt_no = altsetting; |
||||
|
||||
if (ioctl(dpriv->fd, USB_SET_ALTINTERFACE, &intf) < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
return (LIBUSB_SUCCESS); |
||||
} |
||||
|
||||
int |
||||
netbsd_clear_halt(struct libusb_device_handle *handle, unsigned char endpoint) |
||||
{ |
||||
struct device_priv *dpriv = (struct device_priv *)handle->dev->os_priv; |
||||
struct usb_ctl_request req; |
||||
|
||||
usbi_dbg(""); |
||||
|
||||
req.ucr_request.bmRequestType = UT_WRITE_ENDPOINT; |
||||
req.ucr_request.bRequest = UR_CLEAR_FEATURE; |
||||
USETW(req.ucr_request.wValue, UF_ENDPOINT_HALT); |
||||
USETW(req.ucr_request.wIndex, endpoint); |
||||
USETW(req.ucr_request.wLength, 0); |
||||
|
||||
if (ioctl(dpriv->fd, USB_DO_REQUEST, &req) < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
return (LIBUSB_SUCCESS); |
||||
} |
||||
|
||||
int |
||||
netbsd_reset_device(struct libusb_device_handle *handle) |
||||
{ |
||||
usbi_dbg(""); |
||||
|
||||
return (LIBUSB_ERROR_NOT_SUPPORTED); |
||||
} |
||||
|
||||
void |
||||
netbsd_destroy_device(struct libusb_device *dev) |
||||
{ |
||||
struct device_priv *dpriv = (struct device_priv *)dev->os_priv; |
||||
|
||||
usbi_dbg(""); |
||||
|
||||
free(dpriv->cdesc); |
||||
} |
||||
|
||||
int |
||||
netbsd_submit_transfer(struct usbi_transfer *itransfer) |
||||
{ |
||||
struct libusb_transfer *transfer; |
||||
struct handle_priv *hpriv; |
||||
int err = 0; |
||||
|
||||
usbi_dbg(""); |
||||
|
||||
transfer = USBI_TRANSFER_TO_LIBUSB_TRANSFER(itransfer); |
||||
hpriv = (struct handle_priv *)transfer->dev_handle->os_priv; |
||||
|
||||
switch (transfer->type) { |
||||
case LIBUSB_TRANSFER_TYPE_CONTROL: |
||||
err = _sync_control_transfer(itransfer); |
||||
break; |
||||
case LIBUSB_TRANSFER_TYPE_ISOCHRONOUS: |
||||
if (IS_XFEROUT(transfer)) { |
||||
/* Isochronous write is not supported */ |
||||
err = LIBUSB_ERROR_NOT_SUPPORTED; |
||||
break; |
||||
} |
||||
err = _sync_gen_transfer(itransfer); |
||||
break; |
||||
case LIBUSB_TRANSFER_TYPE_BULK: |
||||
case LIBUSB_TRANSFER_TYPE_INTERRUPT: |
||||
if (IS_XFEROUT(transfer) && |
||||
transfer->flags & LIBUSB_TRANSFER_ADD_ZERO_PACKET) { |
||||
err = LIBUSB_ERROR_NOT_SUPPORTED; |
||||
break; |
||||
} |
||||
err = _sync_gen_transfer(itransfer); |
||||
break; |
||||
} |
||||
|
||||
if (err) |
||||
return (err); |
||||
|
||||
if (write(hpriv->pipe[1], &itransfer, sizeof(itransfer)) < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
return (LIBUSB_SUCCESS); |
||||
} |
||||
|
||||
int |
||||
netbsd_cancel_transfer(struct usbi_transfer *itransfer) |
||||
{ |
||||
usbi_dbg(""); |
||||
|
||||
return (LIBUSB_ERROR_NOT_SUPPORTED); |
||||
} |
||||
|
||||
void |
||||
netbsd_clear_transfer_priv(struct usbi_transfer *itransfer) |
||||
{ |
||||
usbi_dbg(""); |
||||
|
||||
/* Nothing to do */ |
||||
} |
||||
|
||||
int |
||||
netbsd_handle_events(struct libusb_context *ctx, struct pollfd *fds, nfds_t nfds, |
||||
int num_ready) |
||||
{ |
||||
struct libusb_device_handle *handle; |
||||
struct handle_priv *hpriv = NULL; |
||||
struct usbi_transfer *itransfer; |
||||
struct pollfd *pollfd; |
||||
int i, err = 0; |
||||
|
||||
usbi_dbg(""); |
||||
|
||||
pthread_mutex_lock(&ctx->open_devs_lock); |
||||
for (i = 0; i < nfds && num_ready > 0; i++) { |
||||
pollfd = &fds[i]; |
||||
|
||||
if (!pollfd->revents) |
||||
continue; |
||||
|
||||
hpriv = NULL; |
||||
num_ready--; |
||||
list_for_each_entry(handle, &ctx->open_devs, list, |
||||
struct libusb_device_handle) { |
||||
hpriv = (struct handle_priv *)handle->os_priv; |
||||
|
||||
if (hpriv->pipe[0] == pollfd->fd) |
||||
break; |
||||
|
||||
hpriv = NULL; |
||||
} |
||||
|
||||
if (NULL == hpriv) { |
||||
usbi_dbg("fd %d is not an event pipe!", pollfd->fd); |
||||
err = ENOENT; |
||||
break; |
||||
} |
||||
|
||||
if (pollfd->revents & POLLERR) { |
||||
usbi_remove_pollfd(HANDLE_CTX(handle), hpriv->pipe[0]); |
||||
usbi_handle_disconnect(handle); |
||||
continue; |
||||
} |
||||
|
||||
if (read(hpriv->pipe[0], &itransfer, sizeof(itransfer)) < 0) { |
||||
err = errno; |
||||
break; |
||||
} |
||||
|
||||
if ((err = usbi_handle_transfer_completion(itransfer, |
||||
LIBUSB_TRANSFER_COMPLETED))) |
||||
break; |
||||
} |
||||
pthread_mutex_unlock(&ctx->open_devs_lock); |
||||
|
||||
if (err) |
||||
return _errno_to_libusb(err); |
||||
|
||||
return (LIBUSB_SUCCESS); |
||||
} |
||||
|
||||
int |
||||
netbsd_clock_gettime(int clkid, struct timespec *tp) |
||||
{ |
||||
usbi_dbg("clock %d", clkid); |
||||
|
||||
if (clkid == USBI_CLOCK_REALTIME) |
||||
return clock_gettime(CLOCK_REALTIME, tp); |
||||
|
||||
if (clkid == USBI_CLOCK_MONOTONIC) |
||||
return clock_gettime(CLOCK_MONOTONIC, tp); |
||||
|
||||
return (LIBUSB_ERROR_INVALID_PARAM); |
||||
} |
||||
|
||||
int |
||||
_errno_to_libusb(int err) |
||||
{ |
||||
switch (err) { |
||||
case EIO: |
||||
return (LIBUSB_ERROR_IO); |
||||
case EACCES: |
||||
return (LIBUSB_ERROR_ACCESS); |
||||
case ENOENT: |
||||
return (LIBUSB_ERROR_NO_DEVICE); |
||||
case ENOMEM: |
||||
return (LIBUSB_ERROR_NO_MEM); |
||||
} |
||||
|
||||
usbi_dbg("error: %s", strerror(err)); |
||||
|
||||
return (LIBUSB_ERROR_OTHER); |
||||
} |
||||
|
||||
int |
||||
_cache_active_config_descriptor(struct libusb_device *dev, int fd) |
||||
{ |
||||
struct device_priv *dpriv = (struct device_priv *)dev->os_priv; |
||||
struct usb_config_desc ucd; |
||||
struct usb_full_desc ufd; |
||||
unsigned char* buf; |
||||
int len; |
||||
|
||||
usbi_dbg("fd %d", fd); |
||||
|
||||
ucd.ucd_config_index = USB_CURRENT_CONFIG_INDEX; |
||||
|
||||
if ((ioctl(fd, USB_GET_CONFIG_DESC, &ucd)) < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
usbi_dbg("active bLength %d", ucd.ucd_desc.bLength); |
||||
|
||||
len = UGETW(ucd.ucd_desc.wTotalLength); |
||||
buf = malloc(len); |
||||
if (buf == NULL) |
||||
return (LIBUSB_ERROR_NO_MEM); |
||||
|
||||
ufd.ufd_config_index = ucd.ucd_config_index; |
||||
ufd.ufd_size = len; |
||||
ufd.ufd_data = buf; |
||||
|
||||
usbi_dbg("index %d, len %d", ufd.ufd_config_index, len); |
||||
|
||||
if ((ioctl(fd, USB_GET_FULL_DESC, &ufd)) < 0) { |
||||
free(buf); |
||||
return _errno_to_libusb(errno); |
||||
} |
||||
|
||||
if (dpriv->cdesc) |
||||
free(dpriv->cdesc); |
||||
dpriv->cdesc = buf; |
||||
|
||||
return (0); |
||||
} |
||||
|
||||
int |
||||
_sync_control_transfer(struct usbi_transfer *itransfer) |
||||
{ |
||||
struct libusb_transfer *transfer; |
||||
struct libusb_control_setup *setup; |
||||
struct device_priv *dpriv; |
||||
struct usb_ctl_request req; |
||||
|
||||
transfer = USBI_TRANSFER_TO_LIBUSB_TRANSFER(itransfer); |
||||
dpriv = (struct device_priv *)transfer->dev_handle->dev->os_priv; |
||||
setup = (struct libusb_control_setup *)transfer->buffer; |
||||
|
||||
usbi_dbg("type %d request %d value %d index %d length %d timeout %d", |
||||
setup->bmRequestType, setup->bRequest, |
||||
libusb_le16_to_cpu(setup->wValue), |
||||
libusb_le16_to_cpu(setup->wIndex), |
||||
libusb_le16_to_cpu(setup->wLength), transfer->timeout); |
||||
|
||||
req.ucr_request.bmRequestType = setup->bmRequestType; |
||||
req.ucr_request.bRequest = setup->bRequest; |
||||
/* Don't use USETW, libusbx already deals with the endianness */ |
||||
(*(uint16_t *)req.ucr_request.wValue) = setup->wValue; |
||||
(*(uint16_t *)req.ucr_request.wIndex) = setup->wIndex; |
||||
(*(uint16_t *)req.ucr_request.wLength) = setup->wLength; |
||||
req.ucr_data = transfer->buffer + LIBUSB_CONTROL_SETUP_SIZE; |
||||
|
||||
if ((transfer->flags & LIBUSB_TRANSFER_SHORT_NOT_OK) == 0) |
||||
req.ucr_flags = USBD_SHORT_XFER_OK; |
||||
|
||||
if ((ioctl(dpriv->fd, USB_SET_TIMEOUT, &transfer->timeout)) < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
if ((ioctl(dpriv->fd, USB_DO_REQUEST, &req)) < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
itransfer->transferred = req.ucr_actlen; |
||||
|
||||
usbi_dbg("transferred %d", itransfer->transferred); |
||||
|
||||
return (0); |
||||
} |
||||
|
||||
int |
||||
_access_endpoint(struct libusb_transfer *transfer) |
||||
{ |
||||
struct handle_priv *hpriv; |
||||
struct device_priv *dpriv; |
||||
char *s, devnode[16]; |
||||
int fd, endpt; |
||||
mode_t mode; |
||||
|
||||
hpriv = (struct handle_priv *)transfer->dev_handle->os_priv; |
||||
dpriv = (struct device_priv *)transfer->dev_handle->dev->os_priv; |
||||
|
||||
endpt = UE_GET_ADDR(transfer->endpoint); |
||||
mode = IS_XFERIN(transfer) ? O_RDONLY : O_WRONLY; |
||||
|
||||
usbi_dbg("endpoint %d mode %d", endpt, mode); |
||||
|
||||
if (hpriv->endpoints[endpt] < 0) { |
||||
/* Pick the right node given the control one */ |
||||
strlcpy(devnode, dpriv->devnode, sizeof(devnode)); |
||||
s = strchr(devnode, '.'); |
||||
snprintf(s, 4, ".%02d", endpt); |
||||
|
||||
/* We may need to read/write to the same endpoint later. */ |
||||
if (((fd = open(devnode, O_RDWR)) < 0) && (errno == ENXIO)) |
||||
if ((fd = open(devnode, mode)) < 0) |
||||
return (-1); |
||||
|
||||
hpriv->endpoints[endpt] = fd; |
||||
} |
||||
|
||||
return (hpriv->endpoints[endpt]); |
||||
} |
||||
|
||||
int |
||||
_sync_gen_transfer(struct usbi_transfer *itransfer) |
||||
{ |
||||
struct libusb_transfer *transfer; |
||||
int fd, nr = 1; |
||||
|
||||
transfer = USBI_TRANSFER_TO_LIBUSB_TRANSFER(itransfer); |
||||
|
||||
/*
|
||||
* Bulk, Interrupt or Isochronous transfer depends on the |
||||
* endpoint and thus the node to open. |
||||
*/ |
||||
if ((fd = _access_endpoint(transfer)) < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
if ((ioctl(fd, USB_SET_TIMEOUT, &transfer->timeout)) < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
if (IS_XFERIN(transfer)) { |
||||
if ((transfer->flags & LIBUSB_TRANSFER_SHORT_NOT_OK) == 0) |
||||
if ((ioctl(fd, USB_SET_SHORT_XFER, &nr)) < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
nr = read(fd, transfer->buffer, transfer->length); |
||||
} else { |
||||
nr = write(fd, transfer->buffer, transfer->length); |
||||
} |
||||
|
||||
if (nr < 0) |
||||
return _errno_to_libusb(errno); |
||||
|
||||
itransfer->transferred = nr; |
||||
|
||||
return (0); |
||||
} |
@ -0,0 +1,51 @@
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* poll_posix: poll compatibility wrapper for POSIX systems |
||||
* Copyright © 2013 RealVNC Ltd. |
||||
* |
||||
* This library is free software; you can redistribute it and/or |
||||
* modify it under the terms of the GNU Lesser General Public |
||||
* License as published by the Free Software Foundation; either |
||||
* version 2.1 of the License, or (at your option) any later version. |
||||
* |
||||
* This library is distributed in the hope that it will be useful, |
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
||||
* Lesser General Public License for more details. |
||||
* |
||||
* You should have received a copy of the GNU Lesser General Public |
||||
* License along with this library; if not, write to the Free Software |
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
||||
* |
||||
*/ |
||||
|
||||
#include <unistd.h> |
||||
#include <fcntl.h> |
||||
#include <errno.h> |
||||
#include <stdlib.h> |
||||
|
||||
#include "libusbi.h" |
||||
|
||||
int usbi_pipe(int pipefd[2]) |
||||
{ |
||||
int ret = pipe(pipefd); |
||||
if (ret != 0) { |
||||
return ret; |
||||
} |
||||
ret = fcntl(pipefd[1], F_GETFL); |
||||
if (ret == -1) { |
||||
usbi_dbg("Failed to get pipe fd flags: %d", errno); |
||||
goto err_close_pipe; |
||||
} |
||||
ret = fcntl(pipefd[1], F_SETFL, ret | O_NONBLOCK); |
||||
if (ret != 0) { |
||||
usbi_dbg("Failed to set non-blocking on new pipe: %d", errno); |
||||
goto err_close_pipe; |
||||
} |
||||
|
||||
return 0; |
||||
|
||||
err_close_pipe: |
||||
usbi_close(pipefd[0]); |
||||
usbi_close(pipefd[1]); |
||||
return ret; |
||||
} |
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,131 @@
@@ -0,0 +1,131 @@
|
||||
/*
|
||||
* Windows CE backend for libusbx 1.0 |
||||
* Copyright © 2011-2013 RealVNC Ltd. |
||||
* Portions taken from Windows backend, which is |
||||
* Copyright © 2009-2010 Pete Batard <pbatard@gmail.com> |
||||
* With contributions from Michael Plante, Orin Eman et al. |
||||
* Parts of this code adapted from libusb-win32-v1 by Stephan Meyer |
||||
* Major code testing contribution by Xiaofan Chen |
||||
* |
||||
* This library is free software; you can redistribute it and/or |
||||
* modify it under the terms of the GNU Lesser General Public |
||||
* License as published by the Free Software Foundation; either |
||||
* version 2.1 of the License, or (at your option) any later version. |
||||
* |
||||
* This library is distributed in the hope that it will be useful, |
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
||||
* Lesser General Public License for more details. |
||||
* |
||||
* You should have received a copy of the GNU Lesser General Public |
||||
* License along with this library; if not, write to the Free Software |
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
||||
*/ |
||||
#pragma once |
||||
|
||||
#include "windows_common.h" |
||||
|
||||
#include <windows.h> |
||||
#include "poll_windows.h" |
||||
|
||||
#define MAX_DEVICE_COUNT 256 |
||||
|
||||
// This is a modified dump of the types in the ceusbkwrapper.h library header
|
||||
// with functions transformed into extern pointers.
|
||||
//
|
||||
// This backend dynamically loads ceusbkwrapper.dll and doesn't include
|
||||
// ceusbkwrapper.h directly to simplify the build process. The kernel
|
||||
// side wrapper driver is built using the platform image build tools,
|
||||
// which makes it difficult to reference directly from the libusbx build
|
||||
// system.
|
||||
struct UKW_DEVICE_PRIV; |
||||
typedef struct UKW_DEVICE_PRIV *UKW_DEVICE; |
||||
typedef UKW_DEVICE *PUKW_DEVICE, *LPUKW_DEVICE; |
||||
|
||||
typedef struct { |
||||
UINT8 bLength; |
||||
UINT8 bDescriptorType; |
||||
UINT16 bcdUSB; |
||||
UINT8 bDeviceClass; |
||||
UINT8 bDeviceSubClass; |
||||
UINT8 bDeviceProtocol; |
||||
UINT8 bMaxPacketSize0; |
||||
UINT16 idVendor; |
||||
UINT16 idProduct; |
||||
UINT16 bcdDevice; |
||||
UINT8 iManufacturer; |
||||
UINT8 iProduct; |
||||
UINT8 iSerialNumber; |
||||
UINT8 bNumConfigurations; |
||||
} UKW_DEVICE_DESCRIPTOR, *PUKW_DEVICE_DESCRIPTOR, *LPUKW_DEVICE_DESCRIPTOR; |
||||
|
||||
typedef struct { |
||||
UINT8 bmRequestType; |
||||
UINT8 bRequest; |
||||
UINT16 wValue; |
||||
UINT16 wIndex; |
||||
UINT16 wLength; |
||||
} UKW_CONTROL_HEADER, *PUKW_CONTROL_HEADER, *LPUKW_CONTROL_HEADER; |
||||
|
||||
// Collection of flags which can be used when issuing transfer requests
|
||||
/* Indicates that the transfer direction is 'in' */ |
||||
#define UKW_TF_IN_TRANSFER 0x00000001 |
||||
/* Indicates that the transfer direction is 'out' */ |
||||
#define UKW_TF_OUT_TRANSFER 0x00000000 |
||||
/* Specifies that the transfer should complete as soon as possible,
|
||||
* even if no OVERLAPPED structure has been provided. */ |
||||
#define UKW_TF_NO_WAIT 0x00000100 |
||||
/* Indicates that transfers shorter than the buffer are ok */ |
||||
#define UKW_TF_SHORT_TRANSFER_OK 0x00000200 |
||||
#define UKW_TF_SEND_TO_DEVICE 0x00010000 |
||||
#define UKW_TF_SEND_TO_INTERFACE 0x00020000 |
||||
#define UKW_TF_SEND_TO_ENDPOINT 0x00040000 |
||||
/* Don't block when waiting for memory allocations */ |
||||
#define UKW_TF_DONT_BLOCK_FOR_MEM 0x00080000 |
||||
|
||||
/* Value to use when dealing with configuration values, such as UkwGetConfigDescriptor,
|
||||
* to specify the currently active configuration for the device. */ |
||||
#define UKW_ACTIVE_CONFIGURATION -1 |
||||
|
||||
DLL_DECLARE(WINAPI, HANDLE, UkwOpenDriver, ()); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwGetDeviceList, (HANDLE, LPUKW_DEVICE, DWORD, LPDWORD)); |
||||
DLL_DECLARE(WINAPI, void, UkwReleaseDeviceList, (HANDLE, LPUKW_DEVICE, DWORD)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwGetDeviceAddress, (UKW_DEVICE, unsigned char*, unsigned char*, unsigned long*)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwGetDeviceDescriptor, (UKW_DEVICE, LPUKW_DEVICE_DESCRIPTOR)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwGetConfigDescriptor, (UKW_DEVICE, DWORD, LPVOID, DWORD, LPDWORD)); |
||||
DLL_DECLARE(WINAPI, void, UkwCloseDriver, (HANDLE)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwCancelTransfer, (UKW_DEVICE, LPOVERLAPPED, DWORD)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwIssueControlTransfer, (UKW_DEVICE, DWORD, LPUKW_CONTROL_HEADER, LPVOID, DWORD, LPDWORD, LPOVERLAPPED)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwClaimInterface, (UKW_DEVICE, DWORD)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwReleaseInterface, (UKW_DEVICE, DWORD)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwSetInterfaceAlternateSetting, (UKW_DEVICE, DWORD, DWORD)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwClearHaltHost, (UKW_DEVICE, UCHAR)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwClearHaltDevice, (UKW_DEVICE, UCHAR)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwGetConfig, (UKW_DEVICE, PUCHAR)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwSetConfig, (UKW_DEVICE, UCHAR)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwResetDevice, (UKW_DEVICE)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwKernelDriverActive, (UKW_DEVICE, DWORD, PBOOL)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwAttachKernelDriver, (UKW_DEVICE, DWORD)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwDetachKernelDriver, (UKW_DEVICE, DWORD)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwIssueBulkTransfer, (UKW_DEVICE, DWORD, UCHAR, LPVOID, DWORD, LPDWORD, LPOVERLAPPED)); |
||||
DLL_DECLARE(WINAPI, BOOL, UkwIsPipeHalted, (UKW_DEVICE, UCHAR, LPBOOL)); |
||||
|
||||
// Used to determine if an endpoint status really is halted on a failed transfer.
|
||||
#define STATUS_HALT_FLAG 0x1 |
||||
|
||||
struct wince_device_priv { |
||||
UKW_DEVICE dev; |
||||
UKW_DEVICE_DESCRIPTOR desc; |
||||
}; |
||||
|
||||
struct wince_device_handle_priv { |
||||
// This member isn't used, but only exists to avoid an empty structure
|
||||
// for private data for the device handle.
|
||||
int reserved; |
||||
}; |
||||
|
||||
struct wince_transfer_priv { |
||||
struct winfd pollable_fd; |
||||
uint8_t interface_number; |
||||
}; |
||||
|
@ -0,0 +1,108 @@
@@ -0,0 +1,108 @@
|
||||
/*
|
||||
* Windows backend common header for libusbx 1.0 |
||||
* |
||||
* This file brings together header code common between |
||||
* the desktop Windows and Windows CE backends. |
||||
* Copyright © 2012-2013 RealVNC Ltd. |
||||
* Copyright © 2009-2012 Pete Batard <pete@akeo.ie> |
||||
* With contributions from Michael Plante, Orin Eman et al. |
||||
* Parts of this code adapted from libusb-win32-v1 by Stephan Meyer |
||||
* Major code testing contribution by Xiaofan Chen |
||||
* |
||||
* This library is free software; you can redistribute it and/or |
||||
* modify it under the terms of the GNU Lesser General Public |
||||
* License as published by the Free Software Foundation; either |
||||
* version 2.1 of the License, or (at your option) any later version. |
||||
* |
||||
* This library is distributed in the hope that it will be useful, |
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
||||
* Lesser General Public License for more details. |
||||
* |
||||
* You should have received a copy of the GNU Lesser General Public |
||||
* License along with this library; if not, write to the Free Software |
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
||||
*/ |
||||
|
||||
#pragma once |
||||
|
||||
// Windows API default is uppercase - ugh!
|
||||
#if !defined(bool) |
||||
#define bool BOOL |
||||
#endif |
||||
#if !defined(true) |
||||
#define true TRUE |
||||
#endif |
||||
#if !defined(false) |
||||
#define false FALSE |
||||
#endif |
||||
|
||||
#define safe_free(p) do {if (p != NULL) {free((void*)p); p = NULL;}} while(0) |
||||
#define safe_closehandle(h) do {if (h != INVALID_HANDLE_VALUE) {CloseHandle(h); h = INVALID_HANDLE_VALUE;}} while(0) |
||||
#define safe_min(a, b) min((size_t)(a), (size_t)(b)) |
||||
#define safe_strcp(dst, dst_max, src, count) do {memcpy(dst, src, safe_min(count, dst_max)); \ |
||||
((char*)dst)[safe_min(count, dst_max)-1] = 0;} while(0) |
||||
#define safe_strcpy(dst, dst_max, src) safe_strcp(dst, dst_max, src, safe_strlen(src)+1) |
||||
#define safe_strncat(dst, dst_max, src, count) strncat(dst, src, safe_min(count, dst_max - safe_strlen(dst) - 1)) |
||||
#define safe_strcat(dst, dst_max, src) safe_strncat(dst, dst_max, src, safe_strlen(src)+1) |
||||
#define safe_strcmp(str1, str2) strcmp(((str1==NULL)?"<NULL>":str1), ((str2==NULL)?"<NULL>":str2)) |
||||
#define safe_stricmp(str1, str2) _stricmp(((str1==NULL)?"<NULL>":str1), ((str2==NULL)?"<NULL>":str2)) |
||||
#define safe_strncmp(str1, str2, count) strncmp(((str1==NULL)?"<NULL>":str1), ((str2==NULL)?"<NULL>":str2), count) |
||||
#define safe_strlen(str) ((str==NULL)?0:strlen(str)) |
||||
#define safe_sprintf(dst, count, ...) do {_snprintf(dst, count, __VA_ARGS__); (dst)[(count)-1] = 0; } while(0) |
||||
#define safe_stprintf _sntprintf |
||||
#define safe_tcslen(str) ((str==NULL)?0:_tcslen(str)) |
||||
#define safe_unref_device(dev) do {if (dev != NULL) {libusb_unref_device(dev); dev = NULL;}} while(0) |
||||
#define wchar_to_utf8_ms(wstr, str, strlen) WideCharToMultiByte(CP_UTF8, 0, wstr, -1, str, strlen, NULL, NULL) |
||||
#ifndef ARRAYSIZE |
||||
#define ARRAYSIZE(A) (sizeof(A)/sizeof((A)[0])) |
||||
#endif |
||||
|
||||
#define ERR_BUFFER_SIZE 256 |
||||
#define TIMER_REQUEST_RETRY_MS 100 |
||||
#define MAX_TIMER_SEMAPHORES 128 |
||||
|
||||
|
||||
/*
|
||||
* API macros - from libusb-win32 1.x |
||||
*/ |
||||
#define DLL_DECLARE_PREFIXNAME(api, ret, prefixname, name, args) \ |
||||
typedef ret (api * __dll_##name##_t)args; \ |
||||
static __dll_##name##_t prefixname = NULL |
||||
|
||||
#ifndef _WIN32_WCE |
||||
#define DLL_STRINGIFY(dll) #dll |
||||
#define DLL_GET_MODULE_HANDLE(dll) GetModuleHandleA(DLL_STRINGIFY(dll)) |
||||
#define DLL_LOAD_LIBRARY(dll) LoadLibraryA(DLL_STRINGIFY(dll)) |
||||
#else |
||||
#define DLL_STRINGIFY(dll) L#dll |
||||
#define DLL_GET_MODULE_HANDLE(dll) GetModuleHandle(DLL_STRINGIFY(dll)) |
||||
#define DLL_LOAD_LIBRARY(dll) LoadLibrary(DLL_STRINGIFY(dll)) |
||||
#endif |
||||
|
||||
#define DLL_LOAD_PREFIXNAME(dll, prefixname, name, ret_on_failure) \ |
||||
do { \ |
||||
HMODULE h = DLL_GET_MODULE_HANDLE(dll); \ |
||||
if (!h) \ |
||||
h = DLL_LOAD_LIBRARY(dll); \ |
||||
if (!h) { \ |
||||
if (ret_on_failure) { return LIBUSB_ERROR_NOT_FOUND; } \ |
||||
else { break; } \ |
||||
} \ |
||||
prefixname = (__dll_##name##_t)GetProcAddress(h, \ |
||||
DLL_STRINGIFY(name)); \ |
||||
if (prefixname) break; \ |
||||
prefixname = (__dll_##name##_t)GetProcAddress(h, \ |
||||
DLL_STRINGIFY(name) DLL_STRINGIFY(A)); \ |
||||
if (prefixname) break; \ |
||||
prefixname = (__dll_##name##_t)GetProcAddress(h, \ |
||||
DLL_STRINGIFY(name) DLL_STRINGIFY(W)); \ |
||||
if (prefixname) break; \ |
||||
if(ret_on_failure) \ |
||||
return LIBUSB_ERROR_NOT_FOUND; \ |
||||
} while(0) |
||||
|
||||
#define DLL_DECLARE(api, ret, name, args) DLL_DECLARE_PREFIXNAME(api, ret, name, name, args) |
||||
#define DLL_LOAD(dll, name, ret_on_failure) DLL_LOAD_PREFIXNAME(dll, name, name, ret_on_failure) |
||||
#define DLL_DECLARE_PREFIXED(api, ret, prefix, name, args) DLL_DECLARE_PREFIXNAME(api, ret, prefix##name, name, args) |
||||
#define DLL_LOAD_PREFIXED(dll, prefix, name, ret_on_failure) DLL_LOAD_PREFIXNAME(dll, prefix##name, name, ret_on_failure) |
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,184 @@
@@ -0,0 +1,184 @@
|
||||
/*
|
||||
* libusb strerror code |
||||
* Copyright © 2013 Hans de Goede <hdegoede@redhat.com> |
||||
* |
||||
* This library is free software; you can redistribute it and/or |
||||
* modify it under the terms of the GNU Lesser General Public |
||||
* License as published by the Free Software Foundation; either |
||||
* version 2.1 of the License, or (at your option) any later version. |
||||
* |
||||
* This library is distributed in the hope that it will be useful, |
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
||||
* Lesser General Public License for more details. |
||||
* |
||||
* You should have received a copy of the GNU Lesser General Public |
||||
* License along with this library; if not, write to the Free Software |
||||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
||||
*/ |
||||
#include "config.h" |
||||
|
||||
#include <locale.h> |
||||
#include <stdlib.h> |
||||
#include <string.h> |
||||
|
||||
#include "libusb.h" |
||||
#include "libusbi.h" |
||||
|
||||
#if defined(_MSC_VER) |
||||
#define strncasecmp _strnicmp |
||||
#endif |
||||
|
||||
static size_t usbi_locale = 0; |
||||
|
||||
/** \ingroup misc
|
||||
* How to add a new \ref libusb_strerror() translation: |
||||
* <ol> |
||||
* <li> Download the latest \c strerror.c from:<br> |
||||
* https://raw.github.com/libusbx/libusbx/master/libusb/sterror.c </li>
|
||||
* <li> Open the file in an UTF-8 capable editor </li> |
||||
* <li> Add the 2 letter <a href="http://en.wikipedia.org/wiki/List_of_ISO_639-1_codes">ISO 639-1</a> |
||||
* code for your locale at the end of \c usbi_locale_supported[]<br> |
||||
* Eg. for Chinese, you would add "zh" so that: |
||||
* \code... usbi_locale_supported[] = { "en", "nl", "fr" };\endcode |
||||
* becomes: |
||||
* \code... usbi_locale_supported[] = { "en", "nl", "fr", "zh" };\endcode </li> |
||||
* <li> Copy the <tt>{ / * English (en) * / ... }</tt> section and add it at the end of \c usbi_localized_errors<br> |
||||
* Eg. for Chinese, the last section of \c usbi_localized_errors could look like: |
||||
* \code |
||||
* }, { / * Chinese (zh) * / |
||||
* "Success", |
||||
* ... |
||||
* "Other error", |
||||
* } |
||||
* };\endcode </li> |
||||
* <li> Translate each of the English messages from the section you copied into your language </li> |
||||
* <li> Save the file (in UTF-8 format) and send it to \c libusbx-devel\@lists.sourceforge.net </li> |
||||
* </ol> |
||||
*/ |
||||
|
||||
static const char* usbi_locale_supported[] = { "en", "nl", "fr" }; |
||||
static const char* usbi_localized_errors[ARRAYSIZE(usbi_locale_supported)][LIBUSB_ERROR_COUNT] = { |
||||
{ /* English (en) */ |
||||
"Success", |
||||
"Input/Output Error", |
||||
"Invalid parameter", |
||||
"Access denied (insufficient permissions)", |
||||
"No such device (it may have been disconnected)", |
||||
"Entity not found", |
||||
"Resource busy", |
||||
"Operation timed out", |
||||
"Overflow", |
||||
"Pipe error", |
||||
"System call interrupted (perhaps due to signal)", |
||||
"Insufficient memory", |
||||
"Operation not supported or unimplemented on this platform", |
||||
"Other error", |
||||
}, { /* Dutch (nl) */ |
||||
"Gelukt", |
||||
"Invoer-/uitvoerfout", |
||||
"Ongeldig argument", |
||||
"Toegang geweigerd (onvoldoende toegangsrechten)", |
||||
"Apparaat bestaat niet (verbinding met apparaat verbroken?)", |
||||
"Niet gevonden", |
||||
"Apparaat of hulpbron is bezig", |
||||
"Bewerking verlopen", |
||||
"Waarde is te groot", |
||||
"Gebroken pijp", |
||||
"Onderbroken systeemaanroep", |
||||
"Onvoldoende geheugen beschikbaar", |
||||
"Bewerking wordt niet ondersteund", |
||||
"Andere fout", |
||||
}, { /* French (fr) */ |
||||
"Succès", |
||||
"Erreur d'entrée/sortie", |
||||
"Paramètre invalide", |
||||
"Accès refusé (permissions insuffisantes)", |
||||
"Périphérique introuvable (peut-être déconnecté)", |
||||
"Elément introuvable", |
||||
"Resource déjà occupée", |
||||
"Operation expirée", |
||||
"Débordement", |
||||
"Erreur de pipe", |
||||
"Appel système abandonné (peut-être à cause d’un signal)", |
||||
"Mémoire insuffisante", |
||||
"Opération non supportée or non implémentée sur cette plateforme", |
||||
"Autre erreur" |
||||
} |
||||
}; |
||||
|
||||
/** \ingroup misc
|
||||
* Set the language, and only the language, not the encoding! used for |
||||
* translatable libusb messages. |
||||
* |
||||
* This takes a locale string in the default setlocale format: lang[-region] |
||||
* or lang[_country_region][.codeset]. Only the lang part of the string is |
||||
* used, and only 2 letter ISO 639-1 codes are accepted for it, such as "de". |
||||
* The optional region, country_region or codeset parts are ignored. This |
||||
* means that functions which return translatable strings will NOT honor the |
||||
* specified encoding. |
||||
* All strings returned are encoded as UTF-8 strings. |
||||
* |
||||
* If libusb_setlocale() is not called, all messages will be in English. |
||||
* |
||||
* The following functions return translatable strings: libusb_strerror(). |
||||
* Note that the libusb log messages controlled through libusb_set_debug() |
||||
* are not translated, they are always in English. |
||||
* |
||||
* For POSIX UTF-8 environments if you want libusb to follow the standard |
||||
* locale settings, call libusb_setlocale(setlocale(LC_MESSAGES, NULL)), |
||||
* after your app has done its locale setup. |
||||
* |
||||
* \param locale locale-string in the form of lang[_country_region][.codeset] |
||||
* or lang[-region], where lang is a 2 letter ISO 639-1 code |
||||
* \returns LIBUSB_SUCCESS on success |
||||
* \returns LIBUSB_ERROR_INVALID_PARAM if the locale doesn't meet the requirements |
||||
* \returns LIBUSB_ERROR_NOT_FOUND if the requested language is not supported |
||||
* \returns a LIBUSB_ERROR code on other errors |
||||
*/ |
||||
|
||||
int API_EXPORTED libusb_setlocale(const char *locale) |
||||
{ |
||||
size_t i; |
||||
|
||||
if ( (locale == NULL) || (strlen(locale) < 2) |
||||
|| ((strlen(locale) > 2) && (locale[2] != '-') && (locale[2] != '_') && (locale[2] != '.')) ) |
||||
return LIBUSB_ERROR_INVALID_PARAM; |
||||
|
||||
for (i=0; i<ARRAYSIZE(usbi_locale_supported); i++) { |
||||
if (strncasecmp(usbi_locale_supported[i], locale, 2) == 0) |
||||
break; |
||||
} |
||||
if (i >= ARRAYSIZE(usbi_locale_supported)) { |
||||
return LIBUSB_ERROR_NOT_FOUND; |
||||
} |
||||
|
||||
usbi_locale = i; |
||||
|
||||
return LIBUSB_SUCCESS; |
||||
} |
||||
|
||||
/** \ingroup misc
|
||||
* Returns a constant string with a short description of the given error code, |
||||
* this description is intended for displaying to the end user and will be in |
||||
* the language set by libusb_setlocale(). |
||||
* |
||||
* The returned string is encoded in UTF-8. |
||||
* |
||||
* The messages always start with a capital letter and end without any dot. |
||||
* The caller must not free() the returned string. |
||||
* |
||||
* \param errcode the error code whose description is desired |
||||
* \returns a short description of the error code in UTF-8 encoding |
||||
*/ |
||||
DEFAULT_VISIBILITY const char* LIBUSB_CALL libusb_strerror(enum libusb_error errcode) |
||||
{ |
||||
int errcode_index = -errcode; |
||||
|
||||
if ((errcode_index < 0) || (errcode_index >= LIBUSB_ERROR_COUNT)) { |
||||
/* "Other Error", which should always be our last message, is returned */ |
||||
errcode_index = LIBUSB_ERROR_COUNT - 1; |
||||
} |
||||
|
||||
return usbi_localized_errors[usbi_locale][errcode_index]; |
||||
} |
Loading…
Reference in new issue