From ca1e4c83a960d06a59d6b37d4ae9c761eb992e3b Mon Sep 17 00:00:00 2001 From: Luca Longinotti Date: Sat, 31 Jan 2015 19:44:48 +0100 Subject: [PATCH 01/44] Implement USB stream transfers, fully conform with libusb 1.0.19 API. --- src/main/java/org/usb4java/LibUsb.java | 111 +++++++++++++++++++---- src/main/java/org/usb4java/Transfer.java | 22 ++++- 2 files changed, 114 insertions(+), 19 deletions(-) diff --git a/src/main/java/org/usb4java/LibUsb.java b/src/main/java/org/usb4java/LibUsb.java index d85dda1..3d8dbd1 100644 --- a/src/main/java/org/usb4java/LibUsb.java +++ b/src/main/java/org/usb4java/LibUsb.java @@ -441,7 +441,7 @@ public final class LibUsb /** We unwrap the BOS => define its maximum size. */ public static final byte DT_BOS_MAX_SIZE = DT_BOS_SIZE - + BT_USB_2_0_EXTENSION_SIZE + BT_SS_USB_DEVICE_CAPABILITY_SIZE + + BT_USB_2_0_EXTENSION_SIZE + BT_SS_USB_DEVICE_CAPABILITY_SIZE + BT_CONTAINER_ID_SIZE; // Endpoint direction. Values for bit 7 of the endpoint address scheme. @@ -478,6 +478,9 @@ public final class LibUsb /** Interrupt endpoint. */ public static final byte TRANSFER_TYPE_INTERRUPT = 3; + /** Stream endpoint. */ + public static final byte TRANSFER_TYPE_BULK_STREAM = 4; + // Synchronization type for isochronous endpoints. // Values for bits 2:3 of the bmAttributes field in // EndpointDescriptor. @@ -519,7 +522,7 @@ public final class LibUsb /** * Automatically free transfer buffer during {@link #freeTransfer(Transfer)} - * + * * Please note that this flag (which is originally 2) is effectively a no-op * (set to zero) here in the Java wrapper, since the ByteBuffer that acts as * a buffer for transfers is allocated by the JVM and is subject to garbage @@ -594,6 +597,11 @@ public final class LibUsb // Flags for hotplug events + /** + * Default value when not using any flags. + */ + public static final int HOTPLUG_NO_FLAGS = 0; + /** * Arm the callback and fire it for all matching currently attached devices. */ @@ -624,14 +632,14 @@ public final class LibUsb /** * Hotplug callbacks (to correctly manage calls and additional data). */ - private static final ConcurrentMap> hotplugCallbacks = new ConcurrentHashMap>(); /** * Pollfd listeners (to support different listeners for different contexts). */ - private static final ConcurrentMap> pollfdListeners = new ConcurrentHashMap>(); @@ -945,7 +953,7 @@ public static native int getMaxIsoPacketSize(final Device device, * {@link #ERROR_NO_DEVICE} if the device has been disconnected, * another error on other failure */ - public static native int open(final Device device, + public static native int open(final Device device, final DeviceHandle handle); /** @@ -1187,6 +1195,44 @@ public static native int clearHalt(final DeviceHandle handle, */ public static native int resetDevice(final DeviceHandle handle); + /** + * Allocate up to numStreams USB bulk streams on the specified endpoints. + * This function takes an array of endpoints rather then a single endpoint + * because some protocols require that endpoints are setup with similar + * stream ids. All endpoints passed in must belong to the same interface. + * + * Note that this function may return less streams then requested. + * + * Stream id 0 is reserved, and should not be used to communicate with + * devices. If LibUsb.allocStreams() returns with a value of N, you may + * use stream ids 1 to N. + * + * @param handle + * a device handle + * @param numStreams + * number of streams to try to allocate + * @param endpoints + * array of endpoints to allocate streams on + * @return The number of streams allocated, or a LIBUSB_ERROR code + * on failure. + */ + public static native int allocStreams(final DeviceHandle handle, + final int numStreams, final byte[] endpoints); + + /** + * Free USB bulk streams allocated with LibUsb.allocStreams(). + * + * Note streams are automatically free-ed when releasing an interface. + * + * @param handle + * a device handle + * @param endpoints + * array of endpoints to allocate streams on + * @return 0 on success, or a LIBUSB_ERROR code on failure. + */ + public static native int freeStreams(final DeviceHandle handle, + final byte[] endpoints); + /** * Determine if a kernel driver is active on an interface. * @@ -1550,7 +1596,7 @@ public static native int getSsEndpointCompanionDescriptor( /** * Free a superspeed endpoint companion descriptor obtained from - * {@link #getSsEndpointCompanionDescriptor(Context, EndpointDescriptor, + * {@link #getSsEndpointCompanionDescriptor(Context, EndpointDescriptor, * SsEndpointCompanionDescriptor)}. * * It is safe to call this function with a NULL parameter, in which case the @@ -1611,7 +1657,7 @@ public static native int getUsb20ExtensionDescriptor(final Context context, /** * Free a USB 2.0 Extension descriptor obtained from - * {@link #getUsb20ExtensionDescriptor(Context, BosDevCapabilityDescriptor, + * {@link #getUsb20ExtensionDescriptor(Context, BosDevCapabilityDescriptor, * Usb20ExtensionDescriptor)}. * * It is safe to call this function with a NULL parameter, in which case @@ -1646,7 +1692,7 @@ public static native int getSsUsbDeviceCapabilityDescriptor( /** * Free a SuperSpeed USB Device Capability descriptor obtained from - * {@link #getSsUsbDeviceCapabilityDescriptor(Context, + * {@link #getSsUsbDeviceCapabilityDescriptor(Context, * BosDevCapabilityDescriptor, SsUsbDeviceCapabilityDescriptor)}. * * It is safe to call this function with a NULL parameter, @@ -1679,7 +1725,7 @@ public static native int getContainerIdDescriptor(final Context context, /** * Free a Container ID descriptor obtained from - * {@link #getContainerIdDescriptor(Context, BosDevCapabilityDescriptor, + * {@link #getContainerIdDescriptor(Context, BosDevCapabilityDescriptor, * ContainerIdDescriptor)}. * * It is safe to call this function with a NULL parameter, in which case @@ -1712,7 +1758,7 @@ public static int getDescriptor(final DeviceHandle handle, final byte type, final byte index, final ByteBuffer data) { return controlTransfer(handle, ENDPOINT_IN, REQUEST_GET_DESCRIPTOR, - (short) (((type & 0xff) << 8) | (index & 0xff)), (short) 0, + (short) (((type & 0xff) << 8) | (index & 0xff)), (short) 0, data, 1000); } @@ -2059,17 +2105,17 @@ public static native int handleEventsTimeoutCompleted( /** * Handle any pending events. - * + * * Like {@link #handleEventsTimeoutCompleted(Context, long, IntBuffer)}, but * without the completed parameter, calling this function is equivalent to * calling {@link #handleEventsTimeoutCompleted(Context, long, IntBuffer)} * with a NULL completed parameter. - * + * * This function is kept primarily for backwards compatibility. All new code * should call {@link #handleEventsCompleted(Context, IntBuffer)} or * {@link #handleEventsTimeoutCompleted(Context, long, IntBuffer)} to avoid * race conditions. - * + * * @param context * The context to operate on, or NULL for the default context * @param timeout @@ -2121,17 +2167,17 @@ public static native int handleEventsCompleted(final Context context, /** * Handle any pending events by polling file descriptors, without checking * if any other threads are already doing so. - * + * * Must be called with the event lock held, see {@link #lockEvents(Context)} * . - * + * * This function is designed to be called under the situation where you have * taken the event lock and are calling poll()/select() directly on libusb's * file descriptors (as opposed to using {@link #handleEvents(Context)} or * similar). You detect events on libusb's descriptors, so you then call * this function with a zero timeout value (while still holding the event * lock). - * + * * @param context * The context to operate on, or NULL for the default context. * @param timeout @@ -2588,6 +2634,37 @@ public static void fillBulkTransfer(final Transfer transfer, transfer.setCallback(callback); } + /** + * Helper function to populate the required {@link Transfer} fields + * for a bulk transfer using bulk streams. + * + * @param transfer + * The transfer to populate. + * @param handle + * Handle of the device that will handle the transfer. + * @param endpoint + * Address of the endpoint where this transfer will be sent. + * @param streamId + * Bulk stream id for this transfer. + * @param buffer + * Data buffer. + * @param callback + * Callback function to be invoked on transfer completion. + * @param userData + * User data to pass to callback function. + * @param timeout + * Timeout for the transfer in milliseconds. + */ + public static void fillBulkStreamTransfer(final Transfer transfer, + final DeviceHandle handle, final byte endpoint, final int streamId, + final ByteBuffer buffer, final TransferCallback callback, + final Object userData, final long timeout) + { + fillBulkTransfer(transfer, handle, endpoint, buffer, callback, userData, timeout); + transfer.setType(TRANSFER_TYPE_BULK_STREAM); + transfer.setStreamId(streamId); + } + /** * Helper function to populate the required {@link Transfer} fields for an * interrupt transfer. @@ -2844,7 +2921,7 @@ public static synchronized int hotplugRegisterCallback( : (vendorId & 0xFFFF), (productId == LibUsb.HOTPLUG_MATCH_ANY) ? (LibUsb.HOTPLUG_MATCH_ANY) : (productId & 0xFFFF), - (deviceClass == LibUsb.HOTPLUG_MATCH_ANY) ? + (deviceClass == LibUsb.HOTPLUG_MATCH_ANY) ? (LibUsb.HOTPLUG_MATCH_ANY) : (deviceClass & 0xFF), callbackHandle, globalHotplugId); diff --git a/src/main/java/org/usb4java/Transfer.java b/src/main/java/org/usb4java/Transfer.java index 50fc126..828975b 100644 --- a/src/main/java/org/usb4java/Transfer.java +++ b/src/main/java/org/usb4java/Transfer.java @@ -191,7 +191,7 @@ public void setLength(final int length) /** * Native method called internally to set the length of the data buffer. - * + * * @param length * The length to set. */ @@ -277,7 +277,7 @@ public void setBuffer(final ByteBuffer buffer) /** * Native method called internally to set the data buffer. - * + * * @param buffer * The data buffer to set. */ @@ -306,6 +306,24 @@ public void setBuffer(final ByteBuffer buffer) */ public native IsoPacketDescriptor[] isoPacketDesc(); + /** + * Get a transfer's bulk stream id. + * + * @return The stream id for the transfer. + */ + public native int streamId(); + + /** + * Set a transfer's bulk stream id. + * + * Note: users are advised to use LibUsb.fillBulkStreamTransfer() instead + * of calling this function directly. + * + * @param streamId + * The stream id to set. + */ + public native void setStreamId(final int streamId); + @Override public int hashCode() { From 129f8e3569126006616ebf2ad6185e7fa681c8a3 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Tue, 14 Apr 2015 11:28:32 +0200 Subject: [PATCH 02/44] Update dependency and plugin versions --- pom.xml | 40 ++++++++++++++++++++++++++++++---------- 1 file changed, 30 insertions(+), 10 deletions(-) diff --git a/pom.xml b/pom.xml index 1c68f4a..63004f7 100644 --- a/pom.xml +++ b/pom.xml @@ -94,7 +94,7 @@ org.apache.maven.plugins maven-project-info-reports-plugin - 2.7 + 2.8 false false @@ -119,7 +119,7 @@ org.apache.maven.plugins maven-changes-plugin - 2.9 + 2.11 @@ -131,7 +131,7 @@ org.apache.maven.plugins maven-javadoc-plugin - 2.9.1 + 2.10.2 @@ -149,7 +149,27 @@ org.apache.maven.plugins maven-surefire-plugin - 2.16 + 2.18.1 + + + org.apache.maven.plugins + maven-clean-plugin + 2.6.1 + + + org.apache.maven.plugins + maven-deploy-plugin + 2.8.2 + + + org.apache.maven.plugins + maven-install-plugin + 2.5.2 + + + org.apache.maven.plugins + maven-resources-plugin + 2.7 @@ -160,7 +180,7 @@ org.apache.maven.plugins maven-compiler-plugin - 3.1 + 3.3 1.6 1.6 @@ -172,7 +192,7 @@ org.apache.maven.plugins maven-site-plugin - 3.3 + 3.4 false en @@ -188,7 +208,7 @@ org.apache.maven.plugins maven-jar-plugin - 2.4 + 2.6 org.codehaus.plexus @@ -201,7 +221,7 @@ maven-assembly-plugin - 2.4 + 2.5.3 false @@ -301,7 +321,7 @@ junit junit - 4.11 + 4.12 test @@ -349,7 +369,7 @@ org.apache.commons commons-lang3 - 3.2.1 + 3.4 From bf4bb8601b1d60e53fd1032230dd9939e463ade4 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Tue, 14 Apr 2015 11:28:44 +0200 Subject: [PATCH 03/44] Fix unit test. Obviously libusb has changed the returned error code --- src/test/java/org/usb4java/LibUsbDeviceTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/test/java/org/usb4java/LibUsbDeviceTest.java b/src/test/java/org/usb4java/LibUsbDeviceTest.java index 85356bb..0fa9e6e 100644 --- a/src/test/java/org/usb4java/LibUsbDeviceTest.java +++ b/src/test/java/org/usb4java/LibUsbDeviceTest.java @@ -208,7 +208,7 @@ public void testGetPortNumbersWithTooSmallBuffer() assumeNotNull(this.device); final ByteBuffer path = BufferUtils.allocateByteBuffer(0); final int result = LibUsb.getPortNumbers(this.device, path); - assertEquals(LibUsb.ERROR_OVERFLOW, result); + assertEquals(LibUsb.ERROR_INVALID_PARAM, result); } /** From 4711217eb3365fe1339d21fe3c96881586588ef6 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 27 Apr 2015 13:40:52 +0200 Subject: [PATCH 04/44] No extra library needed anymore on windows --- src/main/java/org/usb4java/Loader.java | 14 +++++--------- 1 file changed, 5 insertions(+), 9 deletions(-) diff --git a/src/main/java/org/usb4java/Loader.java b/src/main/java/org/usb4java/Loader.java index bbf6f0e..4506ff9 100644 --- a/src/main/java/org/usb4java/Loader.java +++ b/src/main/java/org/usb4java/Loader.java @@ -149,7 +149,7 @@ private static String getExt() } throw new LoaderException("Unable to determine the shared library " + "file extension for operating system '" + os - + "'. Please specify Java parameter -D" + key + + "'. Please specify Java parameter -D" + key + "="); } @@ -214,17 +214,13 @@ private static String getLibName() /** * Returns the name of the libusb native library. This could be * "libusb0.dll" for example or null if this library is not needed on the - * current platform (Because it is provided by the operating system). + * current platform (Because it is provided by the operating system or + * statically linked into the libusb4java library). * * @return The libusb native library name or null if not needed. */ private static String getExtraLibName() { - final String os = getOS(); - if (os.equals(OS_WINDOWS)) - { - return "libusb-1.0." + EXT_DLL; - } return null; } @@ -266,7 +262,7 @@ private static void copy(final InputStream input, final File output) * The library name to extract (For example "libusb0.dll") * @return The absolute path to the extracted library. */ - private static String extractLibrary(final String platform, + private static String extractLibrary(final String platform, final String lib) { // Extract the usb4java library @@ -346,7 +342,7 @@ public static synchronized void load() { return; } - + loaded = true; final String platform = getPlatform(); final String lib = getLibName(); From ff28955cd47086afb2c0eb338787440dce3744c8 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 27 Apr 2015 13:47:29 +0200 Subject: [PATCH 05/44] Fix NPE when USB tests are disabled --- .../org/usb4java/DeviceListIteratorTest.java | 19 +++++++++++-------- 1 file changed, 11 insertions(+), 8 deletions(-) diff --git a/src/test/java/org/usb4java/DeviceListIteratorTest.java b/src/test/java/org/usb4java/DeviceListIteratorTest.java index a78f057..dd16e17 100644 --- a/src/test/java/org/usb4java/DeviceListIteratorTest.java +++ b/src/test/java/org/usb4java/DeviceListIteratorTest.java @@ -24,7 +24,7 @@ public class DeviceListIteratorTest { /** The test subject. */ private DeviceListIterator iterator; - + /** * Setup test. */ @@ -51,11 +51,11 @@ public void tearDown() LibUsb.exit(null); } } - + /** * Tests the {@link DeviceListIterator#hasNext()} method. It just checks * that this call doesn't crash because we can't assume that a device is - * connected at all. + * connected at all. */ @Test public void testHasNext() @@ -63,7 +63,7 @@ public void testHasNext() assumeUsbTestsEnabled(); this.iterator.hasNext(); } - + /** * Tests the {@link DeviceListIterator#next()} method. */ @@ -74,9 +74,9 @@ public void testNext() while (this.iterator.hasNext()) { assertNotNull(this.iterator.next()); - } + } } - + /** * Ensures that {@link DeviceListIterator#next()} method throws * a {@link NoSuchElementException} when accessing elements after the end @@ -85,10 +85,12 @@ public void testNext() public void testNextAfterend() { assumeUsbTestsEnabled(); - while (this.iterator.hasNext()) this.iterator.next(); + while (this.iterator.hasNext()) { + this.iterator.next(); + } this.iterator.next(); } - + /** * Ensures that {@link DeviceListIterator#remove()} throws an exception * because the list is read-only. @@ -96,6 +98,7 @@ public void testNextAfterend() @Test(expected = UnsupportedOperationException.class) public void testRemove() { + assumeUsbTestsEnabled(); this.iterator.remove(); } } From 33e177b4c79bf10b53db7173d21e6ece48189dcf Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 25 May 2015 18:20:06 +0200 Subject: [PATCH 06/44] Change license to MIT --- LICENSE.md | 187 ++++--------------------------------- pom.xml | 2 +- src/site/xdoc/index.xml.vm | 31 ++++-- 3 files changed, 43 insertions(+), 177 deletions(-) diff --git a/LICENSE.md b/LICENSE.md index 7da529f..e7f8f8b 100644 --- a/LICENSE.md +++ b/LICENSE.md @@ -1,167 +1,20 @@ -GNU LESSER GENERAL PUBLIC LICENSE -================================= - -Version 3, 29 June 2007 - -Copyright (C) 2007 Free Software Foundation, Inc. - -Everyone is permitted to copy and distribute verbatim copies of this license -document, but changing it is not allowed. - -This version of the GNU Lesser General Public License incorporates the terms -and conditions of version 3 of the GNU General Public License, supplemented -by the additional permissions listed below. - - -### 0. Additional Definitions. - -As used herein, "this License" refers to version 3 of the GNU Lesser General -Public License, and the "GNU GPL" refers to version 3 of the GNU General -Public License. - -"The Library" refers to a covered work governed by this License, other than -an Application or a Combined Work as defined below. - -An "Application" is any work that makes use of an interface provided by the -Library, but which is not otherwise based on the Library. Defining a -subclass of a class defined by the Library is deemed a mode of using an -interface provided by the Library. - -A "Combined Work" is a work produced by combining or linking an Application -with the Library. The particular version of the Library with which the -Combined Work was made is also called the "Linked Version". - -The "Minimal Corresponding Source" for a Combined Work means the -Corresponding Source for the Combined Work, excluding any source code for -portions of the Combined Work that, considered in isolation, are based on -the Application, and not on the Linked Version. - -The "Corresponding Application Code" for a Combined Work means the object -code and/or source code for the Application, including any data and utility -programs needed for reproducing the Combined Work from the Application, but -excluding the System Libraries of the Combined Work. - - -### 1. Exception to Section 3 of the GNU GPL. - -You may convey a covered work under sections 3 and 4 of this License without -being bound by section 3 of the GNU GPL. - - -### 2. Conveying Modified Versions. - -If you modify a copy of the Library, and, in your modifications, a facility -refers to a function or data to be supplied by an Application that uses the -facility (other than as an argument passed when the facility is invoked), -then you may convey a copy of the modified version: - -* a) under this License, provided that you make a good faith effort to - ensure that, in the event an Application does not supply the function - or data, the facility still operates, and performs whatever part of its - purpose remains meaningful, or - -* b) under the GNU GPL, with none of the additional permissions of this - License applicable to that copy. - - -### 3. Object Code Incorporating Material from Library Header Files. - -The object code form of an Application may incorporate material from a -header file that is part of the Library. You may convey such object code -under terms of your choice, provided that, if the incorporated material is -not limited to numerical parameters, data structure layouts and accessors, -or small macros, inline functions and templates (ten or fewer lines in -length), you do both of the following: - -* a) Give prominent notice with each copy of the object code that the - Library is used in it and that the Library and its use are covered by - this License. - -* b) Accompany the object code with a copy of the GNU GPL and this license - document. - - -### 4. Combined Works. - -You may convey a Combined Work under terms of your choice that, taken -together, effectively do not restrict modification of the portions of the -Library contained in the Combined Work and reverse engineering for debugging -such modifications, if you also do each of the following: - -* a) Give prominent notice with each copy of the Combined Work that the - Library is used in it and that the Library and its use are covered by - this License. - -* b) Accompany the Combined Work with a copy of the GNU GPL and this license - document. - -* c) For a Combined Work that displays copyright notices during execution, - include the copyright notice for the Library among these notices, as - well as a reference directing the user to the copies of the GNU GPL and - this license document. - -* d) Do one of the following: - - * 0) Convey the Minimal Corresponding Source under the terms of this - License, and the Corresponding Application Code in a form suitable - for, and under terms that permit, the user to recombine or relink - the Application with a modified version of the Linked Version to - produce a modified Combined Work, in the manner specified by - section 6 of the GNU GPL for conveying Corresponding Source. - - * 1) Use a suitable shared library mechanism for linking with the - Library. A suitable mechanism is one that (a) uses at run time a - copy of the Library already present on the user's computer system, - and (b) will operate properly with a modified version of the - Library that is interface-compatible with the Linked Version. - -* e) Provide Installation Information, but only if you would otherwise be - required to provide such information under section 6 of the GNU GPL, - and only to the extent that such information is necessary to install - and execute a modified version of the Combined Work produced by - recombining or relinking the Application with a modified version of the - Linked Version. (If you use option 4d0, the Installation Information - must accompany the Minimal Corresponding Source and Corresponding - Application Code. If you use option 4d1, you must provide the - Installation Information in the manner specified by section 6 of the - GNU GPL for conveying Corresponding Source.) - - -### 5. Combined Libraries. - -You may place library facilities that are a work based on the Library side -by side in a single library together with other library facilities that are -not Applications and are not covered by this License, and convey such a -combined library under terms of your choice, if you do both of the -following: - -* a) Accompany the combined library with a copy of the same work based on - the Library, uncombined with any other library facilities, conveyed - under the terms of this License. - -* b) Give prominent notice with the combined library that part of it is a - work based on the Library, and explaining where to find the - accompanying uncombined form of the same work. - - -### 6. Revised Versions of the GNU Lesser General Public License. - -The Free Software Foundation may publish revised and/or new versions of the -GNU Lesser General Public License from time to time. Such new versions will -be similar in spirit to the present version, but may differ in detail to -address new problems or concerns. - -Each version is given a distinguishing version number. If the Library as you -received it specifies that a certain numbered version of the GNU Lesser -General Public License "or any later version" applies to it, you have the -option of following the terms and conditions either of that published -version or of any later version published by the Free Software Foundation. -If the Library as you received it does not specify a version number of the -GNU Lesser General Public License, you may choose any version of the GNU -Lesser General Public License ever published by the Free Software -Foundation. - -If the Library as you received it specifies that a proxy can decide whether -future versions of the GNU Lesser General Public License shall apply, that -proxy's public statement of acceptance of any version is permanent -authorization for you to choose that version for the Library. +Copyright (C) 2011 Klaus Reimer, k@ailis.de +Copyright (C) 2013 Luca Longinotti, l@longi.li + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. \ No newline at end of file diff --git a/pom.xml b/pom.xml index 63004f7..ad9d51f 100644 --- a/pom.xml +++ b/pom.xml @@ -19,7 +19,7 @@ - LGPL + MIT LICENSE.md repo diff --git a/src/site/xdoc/index.xml.vm b/src/site/xdoc/index.xml.vm index a644f2c..9891d14 100644 --- a/src/site/xdoc/index.xml.vm +++ b/src/site/xdoc/index.xml.vm @@ -65,17 +65,30 @@

- 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 3 of the - License, or (at your option) any later version. + Copyright (C) 2011 Klaus Reimer, k@ailis.de
+ Copyright (C) 2013 Luca Longinotti, l@longi.li

+

- 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. + Permission is hereby granted, free of charge, to any person obtaining a copy + of this software and associated documentation files (the "Software"), to deal + in the Software without restriction, including without limitation the rights + to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + copies of the Software, and to permit persons to whom the Software is + furnished to do so, subject to the following conditions: +

+

+ The above copyright notice and this permission notice shall be included in + all copies or substantial portions of the Software. +

+

+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + THE SOFTWARE.

From a04d12bbd38ebd26eff0e878251ba329287e9df5 Mon Sep 17 00:00:00 2001 From: Luca Longinotti Date: Mon, 3 Aug 2015 13:33:15 +0200 Subject: [PATCH 07/44] Update doc as per libusb-1.0.20-rc1. --- src/main/java/org/usb4java/ConfigDescriptor.java | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/main/java/org/usb4java/ConfigDescriptor.java b/src/main/java/org/usb4java/ConfigDescriptor.java index b741391..60cb03c 100644 --- a/src/main/java/org/usb4java/ConfigDescriptor.java +++ b/src/main/java/org/usb4java/ConfigDescriptor.java @@ -107,9 +107,10 @@ public long getPointer() public native byte bmAttributes(); /** - * Returns the maximum power consumption of the USB device from this bus - * in this configuration when the device is fully operation. Expressed in - * units of 2 mA. + * Returns the maximum power consumption of the USB device from this bus + * configuration when the device is fully operation. Expressed in units + * of 2 mA when the device is operating in high-speed mode and in units + * of 8 mA when the device is operating in super-speed mode. * * @return The maximum power consumption. */ From 5f7063041dd51f87a35121647e394870e7a88e53 Mon Sep 17 00:00:00 2001 From: Lorenzo Pavesi Date: Fri, 17 Feb 2017 15:56:35 +0100 Subject: [PATCH 08/44] Add javadoc for LIBUSB_ERROR_INVALID_PARAM The native function controlTransfer return a LIBUSB_ERROR_INVALID_PARAM in case the transfer size is not supported --- src/main/java/org/usb4java/LibUsb.java | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/main/java/org/usb4java/LibUsb.java b/src/main/java/org/usb4java/LibUsb.java index 3d8dbd1..a84cc27 100644 --- a/src/main/java/org/usb4java/LibUsb.java +++ b/src/main/java/org/usb4java/LibUsb.java @@ -1817,7 +1817,9 @@ public static int getStringDescriptor(final DeviceHandle handle, * {@link #ERROR_TIMEOUT} if the transfer timed out, * {@link #ERROR_PIPE} if the control request was not supported by * the device, {@link #ERROR_NO_DEVICE} if the device has been - * disconnected, another ERROR code on other failures + * disconnected, {@link LIBUSB_ERROR_INVALID_PARAM} if the transfer + * size is larger than the operating system and/or hardware can + * support. Another ERROR code on other failures */ public static native int controlTransfer(final DeviceHandle handle, final byte bmRequestType, final byte bRequest, final short wValue, From 47534f98bc959a4b77499b5979c60af6326c6790 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 7 Oct 2018 10:44:01 +0200 Subject: [PATCH 09/44] Update dependencies --- pom.xml | 64 ++++++++++---------------- src/main/java/org/usb4java/Loader.java | 28 +++++++++-- 2 files changed, 48 insertions(+), 44 deletions(-) diff --git a/pom.xml b/pom.xml index ad9d51f..5ae2ff5 100644 --- a/pom.xml +++ b/pom.xml @@ -6,7 +6,7 @@ usb4java jar usb4java - 1.2.1-SNAPSHOT + 1.3.0-SNAPSHOT http://usb4java.org/ USB library for Java based on libusb and implementing javax-usb (JSR-80). @@ -64,8 +64,8 @@ ${repoBaseUrl}/${project.version}/${project.artifactId}-${project.version} ${repoBaseUrl}-javax/${usb4javaJavaxVersion}/${project.artifactId}-javax-${usb4javaJavaxVersion} - 1.2.1-SNAPSHOT - 1.2.1-SNAPSHOT + 1.3.0-SNAPSHOT + 1.3.0-SNAPSHOT @@ -86,7 +86,7 @@ - 3.0 + 3.0.5 @@ -94,7 +94,7 @@ org.apache.maven.plugins maven-project-info-reports-plugin - 2.8 + 3.0.0 false false @@ -119,7 +119,7 @@ org.apache.maven.plugins maven-changes-plugin - 2.11 + 2.12.1 @@ -131,7 +131,7 @@ org.apache.maven.plugins maven-javadoc-plugin - 2.10.2 + 3.0.1 @@ -149,27 +149,27 @@ org.apache.maven.plugins maven-surefire-plugin - 2.18.1 + 2.22.0 org.apache.maven.plugins maven-clean-plugin - 2.6.1 + 3.1.0 org.apache.maven.plugins maven-deploy-plugin - 2.8.2 + 3.0.0-M1 org.apache.maven.plugins maven-install-plugin - 2.5.2 + 3.0.0-M1 org.apache.maven.plugins maven-resources-plugin - 2.7 + 3.1.0 @@ -180,7 +180,7 @@ org.apache.maven.plugins maven-compiler-plugin - 3.3 + 3.8.0 1.6 1.6 @@ -192,7 +192,7 @@ org.apache.maven.plugins maven-site-plugin - 3.4 + 3.7.1 false en @@ -201,46 +201,30 @@ - org.apache.maven.plugins maven-jar-plugin - 2.6 - - - org.codehaus.plexus - plexus-archiver - 2.4.4 - - + 3.1.0 maven-assembly-plugin - 2.5.3 + 3.1.0 + true false src/main/assembly/tarball.xml src/main/assembly/zip.xml - - - 420 - 493 - 493 - package-assembly package - attached + single @@ -340,36 +324,36 @@ org.usb4java libusb4java ${libusb4java.version} - linux-arm + windows-x86 org.usb4java libusb4java ${libusb4java.version} - windows-x86 + windows-x86_64 org.usb4java libusb4java ${libusb4java.version} - windows-x86_64 + macos-x86_64 org.usb4java libusb4java ${libusb4java.version} - osx-x86 + linux-armhf org.usb4java libusb4java ${libusb4java.version} - osx-x86_64 + linux-arm64 org.apache.commons commons-lang3 - 3.4 + 3.8.1 diff --git a/src/main/java/org/usb4java/Loader.java b/src/main/java/org/usb4java/Loader.java index 4506ff9..7cf85d5 100644 --- a/src/main/java/org/usb4java/Loader.java +++ b/src/main/java/org/usb4java/Loader.java @@ -23,7 +23,7 @@ public final class Loader private static final int BUFFER_SIZE = 8192; /** Constant for OS X operating system. */ - private static final String OS_OSX = "osx"; + private static final String OS_MACOS = "macos"; /** Constant for OS X operating system. */ private static final String OS_MACOSX = "macosx"; @@ -51,6 +51,18 @@ public final class Loader /** Constant for amd64 architecture. */ private static final String ARCH_AMD64 = "amd64"; + + /** Constant for armhf architecture. */ + private static final String ARCH_ARMHF = "armhf"; + + /** Constant for aarch64 architecture. */ + private static final String ARCH_AARCH64 = "aarch64"; + + /** Constant for arm architecture. */ + private static final String ARCH_ARM = "arm"; + + /** Constant for arm64 architecture. */ + private static final String ARCH_ARM64 = "arm64"; /** Constant for so file extension. */ private static final String EXT_SO = "so"; @@ -77,7 +89,7 @@ private Loader() /** * Returns the operating system name. This could be "linux", "windows" or - * "osx" or (for any other non-supported platform) the value of the + * "macos" or (for any other non-supported platform) the value of the * "os.name" property converted to lower case and with removed space * characters. * @@ -93,7 +105,7 @@ private static String getOS() } if (os.equals(OS_MACOSX)) { - return OS_OSX; + return OS_MACOS; } return os; } @@ -118,6 +130,14 @@ private static String getArch() { return ARCH_X86_64; } + if (arch.equals(ARCH_AARCH64)) + { + return ARCH_ARM64; + } + if (arch.equals(ARCH_ARM)) + { + return ARCH_ARMHF; + } return arch; } @@ -143,7 +163,7 @@ private static String getExt() { return EXT_DLL; } - if (os.equals(OS_OSX)) + if (os.equals(OS_MACOS)) { return EXT_DYLIB; } From b2b95dae3989d27d92f46ae5d098fd79530c4130 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 7 Oct 2018 11:04:12 +0200 Subject: [PATCH 10/44] Fix site generation --- pom.xml | 12 +++++++----- src/changes/changes.xml | 11 +++++++++++ src/site/site.xml | 4 ++-- src/site/xdoc/index.xml.vm | 2 +- 4 files changed, 21 insertions(+), 8 deletions(-) diff --git a/pom.xml b/pom.xml index 5ae2ff5..8b1d7dc 100644 --- a/pom.xml +++ b/pom.xml @@ -103,12 +103,11 @@ summary - project-team - mailing-list - issue-tracking + team + mailing-lists + issue-management scm - cim - license + licenses dependencies plugins plugin-management @@ -120,6 +119,9 @@ org.apache.maven.plugins maven-changes-plugin 2.12.1 + + team.html + diff --git a/src/changes/changes.xml b/src/changes/changes.xml index b5f865f..9b1a1c2 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -8,6 +8,17 @@ Klaus Reimer + + + Updated to libusb 1.0.22. + + + Dropped support for 32 bit macOS because XCode no longer supports it. + + + Added support for 64 bit ARM platform. + + Split project into usb4java (Main library), usb4java-javax diff --git a/src/site/site.xml b/src/site/site.xml index 893a967..85b2e71 100644 --- a/src/site/site.xml +++ b/src/site/site.xml @@ -12,12 +12,12 @@ org.apache.maven.skins maven-fluido-skin - 1.3.0 + 1.7 - + ]]> diff --git a/src/site/xdoc/index.xml.vm b/src/site/xdoc/index.xml.vm index 9891d14..090da5c 100644 --- a/src/site/xdoc/index.xml.vm +++ b/src/site/xdoc/index.xml.vm @@ -76,7 +76,7 @@ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: -

+

The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. From 15055c7c0e0589391c72f9397fcd49ee15f39335 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 7 Oct 2018 11:24:52 +0200 Subject: [PATCH 11/44] Fix warning in assembly --- src/main/assembly/tarball.xml | 4 ++-- src/main/assembly/zip.xml | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/main/assembly/tarball.xml b/src/main/assembly/tarball.xml index a37a02d..9b1d4b9 100644 --- a/src/main/assembly/tarball.xml +++ b/src/main/assembly/tarball.xml @@ -9,7 +9,7 @@ - / + LICENSE.md @@ -18,7 +18,7 @@ src/main/assembly - / + README.txt AUTHORS.txt diff --git a/src/main/assembly/zip.xml b/src/main/assembly/zip.xml index 7d043c1..5f37b66 100644 --- a/src/main/assembly/zip.xml +++ b/src/main/assembly/zip.xml @@ -9,7 +9,7 @@ - / + LICENSE.md @@ -18,7 +18,7 @@ src/main/assembly - / + README.txt AUTHORS.txt From 996f4ba7fca2b068127052e3775e370926b50485 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 7 Oct 2018 11:59:42 +0200 Subject: [PATCH 12/44] Get rid of pluginManagement section --- pom.xml | 66 +++++++++++++++++++++++++++------------------------------ 1 file changed, 31 insertions(+), 35 deletions(-) diff --git a/pom.xml b/pom.xml index 8b1d7dc..0453028 100644 --- a/pom.xml +++ b/pom.xml @@ -146,36 +146,6 @@ - - - - org.apache.maven.plugins - maven-surefire-plugin - 2.22.0 - - - org.apache.maven.plugins - maven-clean-plugin - 3.1.0 - - - org.apache.maven.plugins - maven-deploy-plugin - 3.0.0-M1 - - - org.apache.maven.plugins - maven-install-plugin - 3.0.0-M1 - - - org.apache.maven.plugins - maven-resources-plugin - 3.1.0 - - - - @@ -203,11 +173,6 @@ - - org.apache.maven.plugins - maven-jar-plugin - 3.1.0 - @@ -231,6 +196,37 @@ + + + org.apache.maven.plugins + maven-surefire-plugin + 2.22.0 + + + org.apache.maven.plugins + maven-clean-plugin + 3.1.0 + + + org.apache.maven.plugins + maven-deploy-plugin + 3.0.0-M1 + + + org.apache.maven.plugins + maven-install-plugin + 3.0.0-M1 + + + org.apache.maven.plugins + maven-resources-plugin + 3.1.0 + + + org.apache.maven.plugins + maven-jar-plugin + 3.1.0 + From ee67671559ff4841e0e6537d251a1427a852cc56 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 8 Oct 2018 19:54:58 +0200 Subject: [PATCH 13/44] Fix logic bug preventing many unit tests to run on test systems --- src/test/java/org/usb4java/LibUsbDeviceTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/test/java/org/usb4java/LibUsbDeviceTest.java b/src/test/java/org/usb4java/LibUsbDeviceTest.java index 0fa9e6e..5b6a402 100644 --- a/src/test/java/org/usb4java/LibUsbDeviceTest.java +++ b/src/test/java/org/usb4java/LibUsbDeviceTest.java @@ -120,7 +120,7 @@ private Device findTestDevice() { final InterfaceDescriptor ifaceDescriptor = iface .altsetting()[k]; - if (ifaceDescriptor.bNumEndpoints() > 1) + if (ifaceDescriptor.bNumEndpoints() > 0) { this.endpoint = ifaceDescriptor.endpoint()[0] .bEndpointAddress(); From 0172799fcb43d737f890e5299d4a1dfad469ae17 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 8 Oct 2018 20:06:38 +0200 Subject: [PATCH 14/44] 0 port numbers is also ok --- src/test/java/org/usb4java/LibUsbDeviceTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/test/java/org/usb4java/LibUsbDeviceTest.java b/src/test/java/org/usb4java/LibUsbDeviceTest.java index 5b6a402..0bdb523 100644 --- a/src/test/java/org/usb4java/LibUsbDeviceTest.java +++ b/src/test/java/org/usb4java/LibUsbDeviceTest.java @@ -193,7 +193,7 @@ public void testGetPortNumbers() assumeNotNull(this.device); final ByteBuffer path = BufferUtils.allocateByteBuffer(8); final int result = LibUsb.getPortNumbers(this.device, path); - assertTrue(result > 0); + assertTrue(result >= 0); assertTrue(result <= path.capacity()); } From a68a6f33c3ec48c271636e785726e6621c9ba806 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 8 Oct 2018 20:59:42 +0200 Subject: [PATCH 15/44] Implement setOption --- src/changes/changes.xml | 37 +++++---- src/main/java/org/usb4java/LibUsb.java | 92 ++++++++++++++++++++-- src/test/java/org/usb4java/LibUsbTest.java | 47 ++++++++++- 3 files changed, 152 insertions(+), 24 deletions(-) diff --git a/src/changes/changes.xml b/src/changes/changes.xml index 9b1a1c2..e24d8e1 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -1,14 +1,17 @@ - Changelog Klaus Reimer - + + + Wrap new libusb functions: setOption. + Updated to libusb 1.0.22. @@ -25,23 +28,23 @@ (javax-usb extension) and libusb4java (Native code). - Add hotplug support to low-level API. + Add hotplug support to low-level API. - Add asynchronous I/O support to low-level API. + Add asynchronous I/O support to low-level API. - Using reunited libusb/libusbx 1.0.16 as backend. + Using reunited libusb/libusbx 1.0.16 as backend. - Add new libusb constants: LOW_SPEED_OPERATION, FULL_SPEED_OPERATION, + Add new libusb constants: LOW_SPEED_OPERATION, FULL_SPEED_OPERATION, HIGH_SPEED_OPERATION, SUPER_SPEED_OPERATION, BM_LPM_SUPPORT, BM_LTM_SUPPORT, BT_WIRELESS_USB_DEVICE_CAPABILITY, BT_USB_2_0_EXTENSION, BT_SS_USB_DEVICE_CAPABILITY, BT_CONTAINER_ID, CAP_HAS_HOTPLUG, CAP_HAS_HID_ACCESS, CAP_SUPPORTS_DETACH_KERNEL_DRIVER, DT_BOS, - DT_DEVICE_CAPABILITY, DT_SS_ENDPOINT_COMPANION + DT_DEVICE_CAPABILITY, DT_SS_ENDPOINT_COMPANION Wrap new libusb methods: getPortNumbers, setAutoDetachKernelDriver, @@ -62,26 +65,26 @@ - Rewritten library to use libusb 1.0 as backend. + Rewritten library to use libusb 1.0 as backend. Made library loading more universal to support loading shared libraries - for platforms not officially supported by usb4java. + for platforms not officially supported by usb4java. - Add native library for linux-arm platform (Raspberry Pi). + Add native library for linux-arm platform (Raspberry Pi). Native libraries are no longer extracted to a temporary directory when they are not in a JAR file. - + Improve error handling during native lib loading so javax-usb no longer hides the important exceptions. - + Fix logic error in AbstractIrpQueue#isBusy(). - + @@ -108,7 +111,7 @@ - Fixed library paths in dylibs so they can be placed in + Fixed library paths in dylibs so they can be placed in *.app/Contents/MacOS. @@ -141,7 +144,7 @@ libusb reports broken bus root devices when detaching USB devices and when user has no root permissions on linux. Fixed it by - only trusting root devices which are also in the device list of a bus. + only trusting root devices which are also in the device list of a bus. diff --git a/src/main/java/org/usb4java/LibUsb.java b/src/main/java/org/usb4java/LibUsb.java index 3d8dbd1..cf236b8 100644 --- a/src/main/java/org/usb4java/LibUsb.java +++ b/src/main/java/org/usb4java/LibUsb.java @@ -59,6 +59,44 @@ public final class LibUsb */ public static final int LOG_LEVEL_DEBUG = 4; + + // Available option values for {@link #setOption()} + + /** + * Set the log message verbosity. + * + * The default level is {@link #LOG_LEVEL_NONE}, which means no messages are ever + * printed. If you choose to increase the message verbosity level, ensure + * that your application does not close the stderr file descriptor. + * + * You are advised to use level {@link #LOG_LEVEL_WARNING}. libusb is conservative + * with its message logging and most of the time, will only log messages that + * explain error conditions and other oddities. This will help you debug + * your software. + * + * If the LIBUSB_DEBUG environment variable was set when libusb was + * initialized, this function does nothing: the message verbosity is fixed + * to the value in the environment variable. + * + * If libusb was compiled without any message logging, this function does + * nothing: you'll never get any messages. + * + * If libusb was compiled with verbose debug message logging, this function + * does nothing: you'll always get messages from all levels. + */ + public static final int OPTION_LOG_LEVEL = 0; + + /** + * Use the UsbDk backend for a specific context, if available. + * + * This option should be set immediately after calling {@link #init()}, otherwise + * unspecified behavior may occur. + * + * Only valid on Windows. + */ + public static final int OPTION_USE_USBDK = 1; + + // Error codes. Most libusb functions return 0 on success or one of these // codes on failure. You can call errorName() to retrieve a string // representation of an error code. @@ -720,9 +758,53 @@ private LibUsb() * context. * @param level * The log level to set. + * + * @deprecated Use {@link #setOption()} instead using the {@link #OPTION_LOG_LEVEL} option. */ public static native void setDebug(final Context context, final int level); + /** + * Set an option in the library. + * + * Use this function to configure a specific option within the library. + * + * Some options require one or more arguments to be provided. Consult each option's documentation for specific + * requirements. + * + * Since libusb version 1.0.22, LIBUSB_API_VERSION >= 0x01000106 + * + * @param context + * The {@link Context} on which to operate. + * @param option + * Which option to set. + * @return {@link #SUCCESS} on success, {@link #ERROR_INVALID_PARAM} if the option or arguments are invalid, + * {@link #ERROR_NOT_SUPPORTED} if the option is valid but not supported on this platform. + */ + public static int setOption(final Context context, final int option) { + return setOption(context, option, 0); + } + + /** + * Set an option in the library. + * + * Use this function to configure a specific option within the library. + * + * Some options require one or more arguments to be provided. Consult each option's documentation for specific + * requirements. + * + * Since libusb version 1.0.22, LIBUSB_API_VERSION >= 0x01000106 + * + * @param context + * The {@link Context} on which to operate. + * @param option + * Which option to set. + * @param value + * Required argument for the specified option. + * @return {@link #SUCCESS} on success, {@link #ERROR_INVALID_PARAM} if the option or arguments are invalid, + * {@link #ERROR_NOT_SUPPORTED} if the option is valid but not supported on this platform. + */ + public static native int setOption(final Context context, final int option, final int value); + /** * Returns the version of the libusb runtime. * @@ -1462,7 +1544,7 @@ public static native int getStringDescriptorAscii( * A simple wrapper around * {@link #getStringDescriptorAscii(DeviceHandle, byte, StringBuffer)}. * It simply returns the string (maximum length of 127) if possible. If not - * possible (NULL handle or 0-index specified or error occured) then null is + * possible (NULL handle or 0-index specified or error occurred) then null is * returned. * * This method is not part of libusb. @@ -1810,7 +1892,7 @@ public static int getStringDescriptor(final DeviceHandle handle, * A suitably-sized data buffer for either input or output * (depending on direction bits within bmRequestType). * @param timeout - * Timeout (in millseconds) that this function should wait before + * Timeout (in milliseconds) that this function should wait before * giving up due to no response being received. For an unlimited * timeout, use value 0. * @return on success the number of bytes actually transferred, @@ -1854,7 +1936,7 @@ public static native int controlTransfer(final DeviceHandle handle, * @param transferred * Output location for the number of bytes actually transferred. * @param timeout - * timeout (in millseconds) that this function should wait before + * timeout (in milliseconds) that this function should wait before * giving up due to no response being received. For an unlimited * timeout, use value 0. * @return 0 on success (and populates transferred), {@link #ERROR_TIMEOUT} @@ -1901,7 +1983,7 @@ public static native int bulkTransfer(final DeviceHandle handle, * @param transferred * Output location for the number of bytes actually transferred. * @param timeout - * Timeout (in millseconds) that this function should wait before + * Timeout (in milliseconds) that this function should wait before * giving up due to no response being received. For an unlimited * timeout, use value 0. * @return 0 on success (and populates transferred), {@link #ERROR_TIMEOUT} @@ -2018,7 +2100,7 @@ public static native int interruptTransfer(final DeviceHandle handle, * * You only need to use this lock if you are developing an application which * calls poll() or select() on libusb's file descriptors directly, and may - * potentially be handling events from 2 threads simultaenously. If you + * potentially be handling events from 2 threads simultaneously. If you * stick to libusb's event handling loop functions (e.g. * {@link #handleEvents(Context)}) then you do not need to be concerned with * this locking. diff --git a/src/test/java/org/usb4java/LibUsbTest.java b/src/test/java/org/usb4java/LibUsbTest.java index 34cd154..90fd453 100644 --- a/src/test/java/org/usb4java/LibUsbTest.java +++ b/src/test/java/org/usb4java/LibUsbTest.java @@ -192,6 +192,37 @@ public void testGetApiVersion() assertTrue(LibUsb.getApiVersion() >= 0x1000102); } + /** + * Tests the {@link LibUsb#setOption(Context, int, int)} method with valid options and values. + */ + @Test + public void testSetOption() + { + assumeUsbTestsEnabled(); + final Context context = new Context(); + assertEquals(LibUsb.SUCCESS, LibUsb.init(context)); + assertEquals(LibUsb.SUCCESS, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, LibUsb.LOG_LEVEL_NONE)); + assertEquals(LibUsb.SUCCESS, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, LibUsb.LOG_LEVEL_DEBUG)); + if (System.getProperty("os.name").toLowerCase().contains("windows")) { + assertEquals(LibUsb.SUCCESS, LibUsb.setOption(context, LibUsb.OPTION_USE_USBDK)); + } else { + assertEquals(LibUsb.ERROR_NOT_SUPPORTED, LibUsb.setOption(context, LibUsb.OPTION_USE_USBDK)); + } + } + + /** + * Tests the {@link LibUsb#setOption(Context, int, int)} method with invalid options and values. + */ + @Test + public void testSetOptionWithInvalidParameters() + { + assumeUsbTestsEnabled(); + final Context context = new Context(); + assertEquals(LibUsb.SUCCESS, LibUsb.init(context)); + assertEquals(LibUsb.ERROR_INVALID_PARAM, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, 234)); + assertEquals(LibUsb.ERROR_INVALID_PARAM, LibUsb.setOption(context, 123)); + } + /** * Tests the initialization and deinitialization of libusb with default * context. @@ -254,6 +285,7 @@ public void testExitWithUninitializedContext() * context */ @Test(expected = IllegalStateException.class) + @Deprecated public void testSetDebugWithUninitializedContext() { assumeUsbTestsEnabled(); @@ -262,8 +294,19 @@ public void testSetDebugWithUninitializedContext() } /** - * Tests {@link LibUsb#getDeviceList(Context, DeviceList)} method with - * uninitialized USB context. + * Tests {@link LibUsb#setOption(Context, int, int)} method with uninitialized USB context. + */ + @Test(expected = IllegalStateException.class) + @Deprecated + public void testSetOptionWithUninitializedContext() + { + assumeUsbTestsEnabled(); + final Context context = new Context(); + LibUsb.setOption(context, 0); + } + + /** + * Tests {@link LibUsb#getDeviceList(Context, DeviceList)} method with uninitialized USB context. */ @Test(expected = IllegalStateException.class) public void testGetDeviceListWithUninitializedContext() From b0ef2ea31366754d40c013b2182b00c08bbf06b3 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 8 Oct 2018 20:59:53 +0200 Subject: [PATCH 16/44] Fix typos --- .gitignore | 1 + src/main/assembly/README.txt | 2 +- .../java/org/usb4java/DescriptorUtils.java | 9 ++-- .../java/org/usb4java/DeviceDescriptor.java | 46 +++++++++---------- .../SsEndpointCompanionDescriptor.java | 4 +- .../org/usb4java/DeviceListIteratorTest.java | 2 +- .../java/org/usb4java/DeviceListTest.java | 6 +-- .../java/org/usb4java/LibUsbDeviceTest.java | 4 +- .../java/org/usb4java/LibUsbGlobalTest.java | 3 +- .../java/org/usb4java/LibUsbHotplugTest.java | 6 +-- src/test/java/org/usb4java/TransferTest.java | 2 +- .../java/org/usb4java/test/UsbAssume.java | 12 ++--- 12 files changed, 49 insertions(+), 48 deletions(-) diff --git a/.gitignore b/.gitignore index 5a3ecc8..351afa7 100644 --- a/.gitignore +++ b/.gitignore @@ -3,5 +3,6 @@ target .classpath .project .idea +.vscode *.iml hs_err_*.log diff --git a/src/main/assembly/README.txt b/src/main/assembly/README.txt index 62f3f9b..e6b9c1c 100644 --- a/src/main/assembly/README.txt +++ b/src/main/assembly/README.txt @@ -11,6 +11,6 @@ libusb4java-*.jar (The native libraries for the various platforms) commons-lang3-*.jar (Apache Commons Lang library needed by usb4java) If you don't want usb4java to extract the native libraries into a temporary -directoy on each program start then you might want to distribute them in +directory on each program start then you might want to distribute them in extracted form with your application. Just make sure your classpath points to the directory where you extracted the JARs. diff --git a/src/main/java/org/usb4java/DescriptorUtils.java b/src/main/java/org/usb4java/DescriptorUtils.java index a30d1b6..75f281f 100644 --- a/src/main/java/org/usb4java/DescriptorUtils.java +++ b/src/main/java/org/usb4java/DescriptorUtils.java @@ -17,7 +17,7 @@ public final class DescriptorUtils { /** Mapping from USB class id to USB class name. */ - private static final Map CLASS_NAMES = + private static final Map CLASS_NAMES = new HashMap(); static @@ -35,8 +35,7 @@ public final class DescriptorUtils CLASS_NAMES.put(LibUsb.CLASS_SMART_CARD, "Smart Card"); CLASS_NAMES.put(LibUsb.CLASS_CONTENT_SECURITY, "Content Security"); CLASS_NAMES.put(LibUsb.CLASS_VIDEO, "Video"); - CLASS_NAMES.put(LibUsb.CLASS_PERSONAL_HEALTHCARE, - "Personal Healthcare"); + CLASS_NAMES.put(LibUsb.CLASS_PERSONAL_HEALTHCARE, "Personal Healthcare"); CLASS_NAMES.put(LibUsb.CLASS_DIAGNOSTIC_DEVICE, "Diagnostic Device"); CLASS_NAMES.put(LibUsb.CLASS_WIRELESS, "Wireless"); CLASS_NAMES.put(LibUsb.CLASS_APPLICATION, "Application"); @@ -137,7 +136,7 @@ public static String dump(final DeviceDescriptor descriptor) * @param product * The product string or null if unknown. * @param serial - * The serial number strsing or null if unknown. + * The serial number string or null if unknown. * @return The descriptor dump. */ public static String dump(final DeviceDescriptor descriptor, @@ -348,7 +347,7 @@ public static String getUsageTypeName(final byte bmAttributes) return "Feedback"; case LibUsb.ISO_USAGE_TYPE_IMPLICIT: return "Implicit Feedback Data"; - case 3: + case 3: // b11 is considered "Reserved" according to USB 3.0 spec. return "Reserved"; default: diff --git a/src/main/java/org/usb4java/DeviceDescriptor.java b/src/main/java/org/usb4java/DeviceDescriptor.java index a79244d..81804f4 100644 --- a/src/main/java/org/usb4java/DeviceDescriptor.java +++ b/src/main/java/org/usb4java/DeviceDescriptor.java @@ -59,11 +59,11 @@ public long getPointer() { return this.deviceDescriptorPointer; } - + /** * Returns the Java byte buffer which contains the descriptor structure. * - * @return The descriptor structur buffer. + * @return The descriptor structure buffer. */ public ByteBuffer getBuffer() { @@ -72,15 +72,15 @@ public ByteBuffer getBuffer() /** * Returns the size of this descriptor (in bytes). - * - * @return The size of this descriptor (in bytes). + * + * @return The size of this descriptor (in bytes). */ public native byte bLength(); /** * Returns the descriptor type. Will have value {@link LibUsb#DT_DEVICE} - * in this context. - * + * in this context. + * * @return The descriptor type. */ public native byte bDescriptorType(); @@ -88,88 +88,88 @@ public ByteBuffer getBuffer() /** * Returns the USB specification release number in binary-coded decimal. * A value of 0x0200 indicates USB 2.0, 0x0110 indicates USB 1.1, etc. - * + * * @return The USB specification release number. - */ + */ public native short bcdUSB(); /** * Returns the USB-IF class code for the device. See LibUSB.CLASS_* * constants. - * + * * @return The USB-IF class code. */ public native byte bDeviceClass(); /** - * Returns the USB-IF subclass code for the device, qualified by the + * Returns the USB-IF subclass code for the device, qualified by the * bDeviceClass value. - * + * * @return The USB-IF subclass code. - */ + */ public native byte bDeviceSubClass(); /** - * Returns the USB-IF protocol code for the device, qualified by the + * Returns the USB-IF protocol code for the device, qualified by the * bDeviceClass and bDeviceSubClass values. - * + * * @return The USB-IF protocol code. */ public native byte bDeviceProtocol(); /** * Returns the maximum packet size for endpoint 0. - * + * * @return The maximum packet site for endpoint 0. */ public native byte bMaxPacketSize0(); /** * Returns the USB-IF vendor ID. - * + * * @return The vendor ID */ public native short idVendor(); /** * Returns the USB-IF product ID. - * + * * @return The product ID. */ public native short idProduct(); /** * Returns the device release number in binary-coded decimal. - * + * * @return The device release number. */ public native short bcdDevice(); /** * Returns the index of the string descriptor describing manufacturer. - * + * * @return The manufacturer string descriptor index. */ public native byte iManufacturer(); /** * Returns the index of the string descriptor describing product. - * + * * @return The product string descriptor index. */ public native byte iProduct(); /** - * Returns the index of the string descriptor containing device serial + * Returns the index of the string descriptor containing device serial * number. - * + * * @return The serial number string descriptor index. */ public native byte iSerialNumber(); /** * Returns the number of possible configurations. - * + * * @return The number of possible configurations. */ public native byte bNumConfigurations(); diff --git a/src/main/java/org/usb4java/SsEndpointCompanionDescriptor.java b/src/main/java/org/usb4java/SsEndpointCompanionDescriptor.java index 9a63d3a..2093463 100644 --- a/src/main/java/org/usb4java/SsEndpointCompanionDescriptor.java +++ b/src/main/java/org/usb4java/SsEndpointCompanionDescriptor.java @@ -36,7 +36,7 @@ public final class SsEndpointCompanionDescriptor /** * Constructs a new descriptor which can be passed to the - * {@link LibUsb#getSsEndpointCompanionDescriptor(Context, + * {@link LibUsb#getSsEndpointCompanionDescriptor(Context, * EndpointDescriptor, SsEndpointCompanionDescriptor)} * method. */ @@ -144,7 +144,7 @@ public boolean equals(final Object obj) return false; } - final SsEndpointCompanionDescriptor other = + final SsEndpointCompanionDescriptor other = (SsEndpointCompanionDescriptor) obj; return new EqualsBuilder() diff --git a/src/test/java/org/usb4java/DeviceListIteratorTest.java b/src/test/java/org/usb4java/DeviceListIteratorTest.java index dd16e17..212735a 100644 --- a/src/test/java/org/usb4java/DeviceListIteratorTest.java +++ b/src/test/java/org/usb4java/DeviceListIteratorTest.java @@ -82,7 +82,7 @@ public void testNext() * a {@link NoSuchElementException} when accessing elements after the end */ @Test(expected = NoSuchElementException.class) - public void testNextAfterend() + public void testNextAfterEnd() { assumeUsbTestsEnabled(); while (this.iterator.hasNext()) { diff --git a/src/test/java/org/usb4java/DeviceListTest.java b/src/test/java/org/usb4java/DeviceListTest.java index 090abdc..5a0bd1b 100644 --- a/src/test/java/org/usb4java/DeviceListTest.java +++ b/src/test/java/org/usb4java/DeviceListTest.java @@ -76,7 +76,7 @@ public void testEquals() LibUsb.freeDeviceList(b, true); } } - + /** * Tests the {@link DeviceList#hashCode()} method. */ @@ -95,7 +95,7 @@ public void testHashCode() LibUsb.freeDeviceList(list, true); } } - + /** * Tests the {@link DeviceList#toString()} method */ @@ -115,7 +115,7 @@ public void testToString() LibUsb.freeDeviceList(list, true); } } - + /** * Tests the {@link DeviceList#getPointer()} method */ diff --git a/src/test/java/org/usb4java/LibUsbDeviceTest.java b/src/test/java/org/usb4java/LibUsbDeviceTest.java index 0bdb523..abd7d29 100644 --- a/src/test/java/org/usb4java/LibUsbDeviceTest.java +++ b/src/test/java/org/usb4java/LibUsbDeviceTest.java @@ -38,7 +38,7 @@ */ public class LibUsbDeviceTest { - /** The libusb contxet. */ + /** The libusb context. */ private Context context; /** The device to run the tests on. */ @@ -785,7 +785,7 @@ private void validateInterfaceDescriptor(final InterfaceDescriptor desc) } /** - * Validates the specified endpoint desriptor. + * Validates the specified endpoint descriptor. * * @param desc * The endpoint descriptor to validate. diff --git a/src/test/java/org/usb4java/LibUsbGlobalTest.java b/src/test/java/org/usb4java/LibUsbGlobalTest.java index 84c8ecd..10c74fd 100644 --- a/src/test/java/org/usb4java/LibUsbGlobalTest.java +++ b/src/test/java/org/usb4java/LibUsbGlobalTest.java @@ -27,7 +27,7 @@ */ public class LibUsbGlobalTest { - /** The libusb contxet. */ + /** The libusb context. */ private Context context; /** @@ -63,6 +63,7 @@ public void tearDown() * Tests the {@link LibUsb#setDebug(Context, int)} method. */ @Test + @Deprecated public void testSetDebug() { assumeUsbTestsEnabled(); diff --git a/src/test/java/org/usb4java/LibUsbHotplugTest.java b/src/test/java/org/usb4java/LibUsbHotplugTest.java index 1eaadfc..dafa218 100644 --- a/src/test/java/org/usb4java/LibUsbHotplugTest.java +++ b/src/test/java/org/usb4java/LibUsbHotplugTest.java @@ -18,12 +18,12 @@ /** * Tests the hotplug part of the {@link LibUsb} class. - * + * * @author Klaus Reimer (k@ailis.de) */ public class LibUsbHotplugTest { - /** The libusb contxet. */ + /** The libusb context. */ private Context context; /** @@ -95,7 +95,7 @@ public int processEvent(Context context, Device device, } /** - * Ensures that no hotplug event is fired when enumeration is deactived. + * Ensures that no hotplug event is fired when enumeration is deactivated. * When no devices are connected then this test is pretty much useless but * won't fail because of that. */ diff --git a/src/test/java/org/usb4java/TransferTest.java b/src/test/java/org/usb4java/TransferTest.java index facb0e8..c2d852e 100644 --- a/src/test/java/org/usb4java/TransferTest.java +++ b/src/test/java/org/usb4java/TransferTest.java @@ -30,7 +30,7 @@ */ public class TransferTest { - /** The libusb contxet. */ + /** The libusb context. */ private Context context; /** diff --git a/src/test/java/org/usb4java/test/UsbAssume.java b/src/test/java/org/usb4java/test/UsbAssume.java index 1b9f22f..7445ce8 100644 --- a/src/test/java/org/usb4java/test/UsbAssume.java +++ b/src/test/java/org/usb4java/test/UsbAssume.java @@ -15,7 +15,7 @@ /** * USB-related assumptions. - * + * * @author Klaus Reimer (k@ailis.de) */ public class UsbAssume @@ -25,16 +25,16 @@ public class UsbAssume /** If TCK tests are to be executed. */ private static Boolean tckTests; - + /** * Check if USB tests are enabled. - * + * * USB tests can be controlled with the system property USB_TESTS. When * set to true then USB tests are always run, if set to false then they * are never run. If this property is not set then the command-line tool * lsusb is called. If this tool returned at least two lines of text then * USB tests are enabled. In all other cases they are disabled. - * + * * @return True if USB tests are enabled, false if not. */ public static boolean isUsbTestsEnabled() @@ -86,7 +86,7 @@ public static boolean isUsbTestsEnabled() * Assume that USB tests are enabled. Call this in the first line of * tests method or preparation methods when you want to ignore the * tests when the system is not able to run the tests anyway. - * + * * USB tests can be controlled with the system property USB_TESTS. When * set to true then USB tests are always run, if set to false then they * are never run. If this property is not set then the command-line tool @@ -117,7 +117,7 @@ public static void assumeHotplugAvailable() * Assume that TCK tests are enabled. Call this in the first line of * tests method or preparation methods when you want to ignore the * tests when the system is not able to run the TCK tests anyway. - * + * * TCK tests can be controlled with the system property TCK_TESTS. When * set to true then TCK tests are always run, if set to false then they * are never run. If this property is not set then the command-line tool From 054abf6503b2867383fd97c44544fde705b310d7 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 8 Oct 2018 21:05:18 +0200 Subject: [PATCH 17/44] Add missing SPEED_SUPER_PLUS constant --- src/changes/changes.xml | 5 ++++- src/main/java/org/usb4java/LibUsb.java | 4 ++++ 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/src/changes/changes.xml b/src/changes/changes.xml index e24d8e1..559be47 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -9,7 +9,10 @@ - + + Add missing SPEED_SUPER_PLUS constant. + + Wrap new libusb functions: setOption. diff --git a/src/main/java/org/usb4java/LibUsb.java b/src/main/java/org/usb4java/LibUsb.java index cf236b8..b231695 100644 --- a/src/main/java/org/usb4java/LibUsb.java +++ b/src/main/java/org/usb4java/LibUsb.java @@ -163,6 +163,10 @@ public final class LibUsb /** The device is operating at super speed (5000MBit/s). */ public static final int SPEED_SUPER = 4; + /** The device is operating at super speed plus (10000MBit/s). */ + public static final int SPEED_SUPER_PLUS = 5; + + // Supported speeds (wSpeedSupported) bitfield. Indicates what speeds the // device supports. From f0d2b91b1e2f10dd8ef34b39ecf62f02309f3365 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 8 Oct 2018 21:35:34 +0200 Subject: [PATCH 18/44] NOT FOUND error is also ok in unit test --- src/test/java/org/usb4java/LibUsbTest.java | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/src/test/java/org/usb4java/LibUsbTest.java b/src/test/java/org/usb4java/LibUsbTest.java index 90fd453..12e0103 100644 --- a/src/test/java/org/usb4java/LibUsbTest.java +++ b/src/test/java/org/usb4java/LibUsbTest.java @@ -201,13 +201,16 @@ public void testSetOption() assumeUsbTestsEnabled(); final Context context = new Context(); assertEquals(LibUsb.SUCCESS, LibUsb.init(context)); - assertEquals(LibUsb.SUCCESS, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, LibUsb.LOG_LEVEL_NONE)); - assertEquals(LibUsb.SUCCESS, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, LibUsb.LOG_LEVEL_DEBUG)); if (System.getProperty("os.name").toLowerCase().contains("windows")) { - assertEquals(LibUsb.SUCCESS, LibUsb.setOption(context, LibUsb.OPTION_USE_USBDK)); + // On Windows this is either a success when USBDK is found or ERROR_NOT_FOUND when not + final int result = LibUsb.setOption(context, LibUsb.OPTION_USE_USBDK); + assertTrue(result == LibUsb.SUCCESS || result == LibUsb.ERROR_NOT_FOUND); } else { + // On other operating systems it is always ERROR_NOT_SUPPORTED assertEquals(LibUsb.ERROR_NOT_SUPPORTED, LibUsb.setOption(context, LibUsb.OPTION_USE_USBDK)); } + assertEquals(LibUsb.SUCCESS, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, LibUsb.LOG_LEVEL_NONE)); + assertEquals(LibUsb.SUCCESS, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, LibUsb.LOG_LEVEL_DEBUG)); } /** From bddf0cde58d348b5853b1046375229c304026f47 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 8 Oct 2018 22:31:15 +0200 Subject: [PATCH 19/44] Fix typo --- src/test/java/org/usb4java/LibUsbDeviceTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/test/java/org/usb4java/LibUsbDeviceTest.java b/src/test/java/org/usb4java/LibUsbDeviceTest.java index abd7d29..08611fa 100644 --- a/src/test/java/org/usb4java/LibUsbDeviceTest.java +++ b/src/test/java/org/usb4java/LibUsbDeviceTest.java @@ -436,7 +436,7 @@ public void testUnrefDeviceWithoutDevice() * Tests the {@link LibUsb#open(Device, DeviceHandle)} method. This can't be * really tested in a simple unit test like this. Most likely the user has * no access to the device. So this test succeeds on SUCCESS and on - * ERROR_ACCESS. At least we have to make sure then open() method doesn't + * ERROR_ACCESS. At least we have to make sure that the open() method doesn't * crash. */ @Test From 3c37af552fcc59251fdc33aa4e23a2c2997d5a29 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 8 Oct 2018 22:31:54 +0200 Subject: [PATCH 20/44] Wrap new libusb functions: devMemAlloc and devMemFree --- src/changes/changes.xml | 2 +- src/main/java/org/usb4java/LibUsb.java | 41 +++++++++++++++++++++++++- 2 files changed, 41 insertions(+), 2 deletions(-) diff --git a/src/changes/changes.xml b/src/changes/changes.xml index 559be47..fa19243 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -13,7 +13,7 @@ Add missing SPEED_SUPER_PLUS constant. - Wrap new libusb functions: setOption. + Wrap new libusb functions: setOption, devMemAlloc, devMemFree. Updated to libusb 1.0.22. diff --git a/src/main/java/org/usb4java/LibUsb.java b/src/main/java/org/usb4java/LibUsb.java index b231695..762a99d 100644 --- a/src/main/java/org/usb4java/LibUsb.java +++ b/src/main/java/org/usb4java/LibUsb.java @@ -1082,7 +1082,7 @@ public static native DeviceHandle openDeviceWithVidPid( */ public static native void close(final DeviceHandle handle); -/** + /** * Get the underlying device for a handle. * * Please note that the reference count of the returned device is not @@ -1319,6 +1319,45 @@ public static native int allocStreams(final DeviceHandle handle, public static native int freeStreams(final DeviceHandle handle, final byte[] endpoints); + + /** + * Attempts to allocate a block of persistent DMA memory suitable for transfers against the given device. + * + * If successful, will return a block of memory that is suitable for use as "buffer" in {@link Transfer} + * against this device. Using this memory instead of regular memory means that the host controller can use DMA + * directly into the buffer to increase performance, and also that transfers can no longer fail due to kernel + * memory fragmentation. + * + * Note that this means you should not modify this memory (or even data on the same cache lines) when a transfer + * is in progress, although it is legal to have several transfers going on within the same memory block. + * + * Will return NULL on failure. Many systems do not support such zerocopy and will always return NULL. Memory + * allocated with this function must be freed with {@link #devMemFree()}. Specifically, this means that the flag + * {@link #TRANSFER_FREE_BUFFER} cannot be used to free memory allocated with this function. + * + * Since version 1.0.21, LIBUSB_API_VERSION >= 0x01000105 + * + * @param handle + * A device handle. + * @param length + * Size of desired data buffer. + * @return The newly allocated memory, or NULL on failure. + */ + public static native ByteBuffer devMemAlloc(final DeviceHandle handle, final int length); + + /** + * Free device memory allocated with {@link #devMemAlloc()}. + * + * @param handle + * A device handle. + * @param buffer + * The previously allocated memory. + * @param size + * The size of the previously allocated memory. + * @return {@link #SUCCESS}, or a LIBUSB_ERROR code on failure. + */ + public static native int devMemFree(final DeviceHandle handle, final ByteBuffer buffer, final int length); + /** * Determine if a kernel driver is active on an interface. * From 7ab6e6d3ed0d621d26490507b5bc18b52ae330bb Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 8 Oct 2018 22:44:01 +0200 Subject: [PATCH 21/44] Document ERROR_BUSY return value --- src/main/java/org/usb4java/LibUsb.java | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/src/main/java/org/usb4java/LibUsb.java b/src/main/java/org/usb4java/LibUsb.java index 8757f85..2df3077 100644 --- a/src/main/java/org/usb4java/LibUsb.java +++ b/src/main/java/org/usb4java/LibUsb.java @@ -1940,11 +1940,12 @@ public static int getStringDescriptor(final DeviceHandle handle, * timeout, use value 0. * @return on success the number of bytes actually transferred, * {@link #ERROR_TIMEOUT} if the transfer timed out, - * {@link #ERROR_PIPE} if the control request was not supported by - * the device, {@link #ERROR_NO_DEVICE} if the device has been - * disconnected, {@link LIBUSB_ERROR_INVALID_PARAM} if the transfer - * size is larger than the operating system and/or hardware can - * support. Another ERROR code on other failures + * {@link #ERROR_PIPE} if the control request was not supported by the device, + * {@link #ERROR_NO_DEVICE} if the device has been disconnected, + * {@link #ERROR_BUSY} if called from event handling context, + * {@link #ERROR_INVALID_PARAM} if the transfer size is larger than the operating system and/or + * hardware can support. + * Another ERROR code on other failures */ public static native int controlTransfer(final DeviceHandle handle, final byte bmRequestType, final byte bRequest, final short wValue, From b24618df0f0e0ab88ed855604d4c11c7d6ecd91a Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Mon, 8 Oct 2018 22:56:06 +0200 Subject: [PATCH 22/44] Implement interruptEventHandler --- src/changes/changes.xml | 2 +- src/main/java/org/usb4java/LibUsb.java | 13 ++++++++++++ src/test/java/org/usb4java/LibUsbTest.java | 23 ++++++++++++++++++++++ 3 files changed, 37 insertions(+), 1 deletion(-) diff --git a/src/changes/changes.xml b/src/changes/changes.xml index fa19243..493623d 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -13,7 +13,7 @@ Add missing SPEED_SUPER_PLUS constant. - Wrap new libusb functions: setOption, devMemAlloc, devMemFree. + Wrap new libusb functions: setOption, devMemAlloc, devMemFree, interruptEventHandler. Updated to libusb 1.0.22. diff --git a/src/main/java/org/usb4java/LibUsb.java b/src/main/java/org/usb4java/LibUsb.java index 2df3077..c232569 100644 --- a/src/main/java/org/usb4java/LibUsb.java +++ b/src/main/java/org/usb4java/LibUsb.java @@ -2134,6 +2134,19 @@ public static native int interruptTransfer(final DeviceHandle handle, */ public static native int eventHandlerActive(final Context context); + /** + * Interrupt any active thread that is handling events. + * + * This is mainly useful for interrupting a dedicated event handling thread when an application wishes to call + * {@link #exit()}. + * + * Since version 1.0.21, LIBUSB_API_VERSION >= 0x01000105 + * + * @param ctx + * The context to operate on, or NULL for the default context. + */ + public static native void interruptEventHandler(final Context context); + /** * Acquire the event waiters lock. * diff --git a/src/test/java/org/usb4java/LibUsbTest.java b/src/test/java/org/usb4java/LibUsbTest.java index 12e0103..9dba00c 100644 --- a/src/test/java/org/usb4java/LibUsbTest.java +++ b/src/test/java/org/usb4java/LibUsbTest.java @@ -1098,6 +1098,17 @@ public void testEventHandlerActiveWithUninitializedContext() LibUsb.eventHandlerActive(context); } + /** + * Tests {@link LibUsb#interruptEventHandler(Context)} with uninitialized USB context. + */ + @Test(expected = IllegalStateException.class) + public void testInterruptEventHandlerWithUninitializedContext() + { + assumeUsbTestsEnabled(); + final Context context = new Context(); + LibUsb.interruptEventHandler(context); + } + /** * Tests {@link LibUsb#lockEventWaiters(Context)} with uninitialized USB * context. @@ -1297,4 +1308,16 @@ public void testPollFdNotifiers() assertNull(listener.removedFd); assertNull(listener.removedUserData); } + + /** + * Tests the {@link LibUsb#interruptEventHandler(Context)} method. Must not crash. + */ + @Test + public void testInterruptEventHandler() + { + assumeUsbTestsEnabled(); + final Context context = new Context(); + assertEquals(LibUsb.SUCCESS, LibUsb.init(context)); + LibUsb.interruptEventHandler(context); + } } From b762fb3f016eec3801113fef5caf2bac5e220ae6 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Tue, 9 Oct 2018 00:14:26 +0200 Subject: [PATCH 23/44] Add more unit tests for GetDeviceList --- src/test/java/org/usb4java/LibUsbTest.java | 51 ++++++++++++++++++++++ 1 file changed, 51 insertions(+) diff --git a/src/test/java/org/usb4java/LibUsbTest.java b/src/test/java/org/usb4java/LibUsbTest.java index 9dba00c..27fa5fc 100644 --- a/src/test/java/org/usb4java/LibUsbTest.java +++ b/src/test/java/org/usb4java/LibUsbTest.java @@ -308,6 +308,47 @@ public void testSetOptionWithUninitializedContext() LibUsb.setOption(context, 0); } + /** + * Tests {@link LibUsb#getDeviceList(Context, DeviceList)} method. + */ + @Test + public void testGetDeviceList() + { + assumeUsbTestsEnabled(); + final Context context = new Context(); + final DeviceList deviceList = new DeviceList(); + LibUsb.init(context); + try + { + assertTrue(LibUsb.getDeviceList(context, deviceList) >= 0); + LibUsb.freeDeviceList(deviceList, true); + } + finally + { + LibUsb.exit(context); + } + } + + /** + * Tests {@link LibUsb#getDeviceList(Context, DeviceList)} method with the default context. + */ + @Test + public void testGetDeviceListFromDefaultContext() + { + assumeUsbTestsEnabled(); + final DeviceList deviceList = new DeviceList(); + LibUsb.init(null); + try + { + assertTrue(LibUsb.getDeviceList(null, deviceList) >= 0); + LibUsb.freeDeviceList(deviceList, true); + } + finally + { + LibUsb.exit(null); + } + } + /** * Tests {@link LibUsb#getDeviceList(Context, DeviceList)} method with uninitialized USB context. */ @@ -319,6 +360,16 @@ public void testGetDeviceListWithUninitializedContext() LibUsb.getDeviceList(context, new DeviceList()); } + /** + * Tests {@link LibUsb#getDeviceList(Context, DeviceList)} method with uninitialized default USB context. + */ + @Test(expected = IllegalStateException.class) + public void testGetDeviceListWithUninitializedDefaultContext() + { + assumeUsbTestsEnabled(); + LibUsb.getDeviceList(null, new DeviceList()); + } + /** * Tests {@link LibUsb#freeDeviceList(DeviceList, boolean)} method with * uninitialized list. From 0f092ba635dc4b836391127c14d8ea8b1232e4f5 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Tue, 9 Oct 2018 00:23:55 +0200 Subject: [PATCH 24/44] Remove broken build status --- README.md | 2 -- 1 file changed, 2 deletions(-) diff --git a/README.md b/README.md index c76524f..5636524 100644 --- a/README.md +++ b/README.md @@ -21,5 +21,3 @@ and loaded so you don't need to care about them. For more detailed information please visit the [usb4java website](http://usb4java.org/). -[![Build Status](https://ci.ailis.de/job/usb4java/badge/icon)](https://ci.ailis.de/job/usb4java/) - From 2bd1cb8d9ef141314d75283140730345a3877789 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Wed, 10 Oct 2018 23:11:21 +0200 Subject: [PATCH 25/44] Use new os and arch names --- pom.xml | 94 +++++++++++++------------- src/main/java/org/usb4java/Loader.java | 87 +++++------------------- 2 files changed, 65 insertions(+), 116 deletions(-) diff --git a/pom.xml b/pom.xml index 0453028..ecb357d 100644 --- a/pom.xml +++ b/pom.xml @@ -1,7 +1,7 @@ 4.0.0 - + org.usb4java usb4java jar @@ -16,7 +16,7 @@ usb4java Team http://usb4java.org/ - + MIT @@ -24,7 +24,7 @@ repo - + Discussions @@ -32,9 +32,9 @@ usb4java+unsubscribe@googlegroups.com usb4java@googlegroups.com http://groups.google.com/group/usb4java - - - + + + kayahr @@ -45,7 +45,7 @@ +1 http://www.ailis.de/~k/ - + llongi Luca Longinotti @@ -55,7 +55,7 @@ +1 http://l.longi.li/ - + @@ -67,28 +67,28 @@ 1.3.0-SNAPSHOT 1.3.0-SNAPSHOT - + scm:git:git://github.com/usb4java/${project.artifactId}.git scm:git:ssh://git@github.com/usb4java/${project.artifactId}.git http://github.com/usb4java/${project.artifactId} HEAD - + GitHub https://github.com/usb4java/${project.artifactId}/issues - + Jenkins https://ci.ailis.de/job/${project.artifactId}/ - + 3.0.5 - + @@ -111,11 +111,11 @@ dependencies plugins plugin-management - - - + + + - + org.apache.maven.plugins maven-changes-plugin 2.12.1 @@ -142,12 +142,12 @@ - - - + + + - + org.apache.maven.plugins @@ -159,11 +159,11 @@ ${project.build.sourceEncoding} - + org.apache.maven.plugins - maven-site-plugin + maven-site-plugin 3.7.1 false @@ -172,10 +172,10 @@ ${project.build.sourceEncoding} - + - + maven-assembly-plugin 3.1.0 @@ -194,7 +194,7 @@ single - + @@ -224,12 +224,12 @@ org.apache.maven.plugins - maven-jar-plugin + maven-jar-plugin 3.1.0 - - + + - + ailis @@ -284,7 +284,7 @@ sonatype-snapshots Sonatype Snapshot Repository https://oss.sonatype.org/content/repositories/snapshots - + --> ailis-releases @@ -295,10 +295,10 @@ ailis-snapshots Ailis Maven Snapshots http://nexus.ailis.de/content/repositories/snapshots - + - + junit @@ -311,48 +311,48 @@ libusb4java ${libusb4java.version} linux-x86 - + org.usb4java libusb4java ${libusb4java.version} - linux-x86_64 - + linux-x86-64 + org.usb4java libusb4java ${libusb4java.version} - windows-x86 - + win32-x86 + org.usb4java libusb4java ${libusb4java.version} - windows-x86_64 - + win32-x86-64 + org.usb4java libusb4java ${libusb4java.version} - macos-x86_64 - + darwin-x86-64 + org.usb4java libusb4java ${libusb4java.version} - linux-armhf - + linux-arm + org.usb4java libusb4java ${libusb4java.version} - linux-arm64 - + linux-aarch64 + org.apache.commons commons-lang3 3.8.1 - + diff --git a/src/main/java/org/usb4java/Loader.java b/src/main/java/org/usb4java/Loader.java index 7cf85d5..e6917d0 100644 --- a/src/main/java/org/usb4java/Loader.java +++ b/src/main/java/org/usb4java/Loader.java @@ -22,57 +22,6 @@ public final class Loader /** Buffer size used for copying data. */ private static final int BUFFER_SIZE = 8192; - /** Constant for OS X operating system. */ - private static final String OS_MACOS = "macos"; - - /** Constant for OS X operating system. */ - private static final String OS_MACOSX = "macosx"; - - /** Constant for Linux operating system. */ - private static final String OS_LINUX = "linux"; - - /** Constant for Windows operating system. */ - private static final String OS_WINDOWS = "windows"; - - /** Constant for FreeBSD operating system. */ - private static final String OS_FREEBSD = "freebsd"; - - /** Constant for SunOS operating system. */ - private static final String OS_SUNOS = "sunos"; - - /** Constant for i386 architecture. */ - private static final String ARCH_I386 = "i386"; - - /** Constant for x86 architecture. */ - private static final String ARCH_X86 = "x86"; - - /** Constant for x86_64 architecture. */ - private static final String ARCH_X86_64 = "x86_64"; - - /** Constant for amd64 architecture. */ - private static final String ARCH_AMD64 = "amd64"; - - /** Constant for armhf architecture. */ - private static final String ARCH_ARMHF = "armhf"; - - /** Constant for aarch64 architecture. */ - private static final String ARCH_AARCH64 = "aarch64"; - - /** Constant for arm architecture. */ - private static final String ARCH_ARM = "arm"; - - /** Constant for arm64 architecture. */ - private static final String ARCH_ARM64 = "arm64"; - - /** Constant for so file extension. */ - private static final String EXT_SO = "so"; - - /** Constant for dll file extension. */ - private static final String EXT_DLL = "dll"; - - /** Constant for dylib file extension. */ - private static final String EXT_DYLIB = "dylib"; - /** The temporary directory for native libraries. */ private static File tmp; @@ -99,13 +48,13 @@ private static String getOS() { final String os = System.getProperty("os.name").toLowerCase() .replace(" ", ""); - if (os.contains(OS_WINDOWS)) + if (os.contains("windows")) { - return OS_WINDOWS; + return "win32"; } - if (os.equals(OS_MACOSX)) + if (os.equals("macosx") || os.equals("macos")) { - return OS_MACOS; + return "darwin"; } return os; } @@ -122,21 +71,21 @@ private static String getArch() { final String arch = System.getProperty("os.arch").toLowerCase() .replace(" ", ""); - if (arch.equals(ARCH_I386)) + if (arch.equals("i386")) { - return ARCH_X86; + return "x86"; } - if (arch.equals(ARCH_AMD64)) + if (arch.equals("amd64") || arch.equals("x86_64")) { - return ARCH_X86_64; + return "x86-64"; } - if (arch.equals(ARCH_AARCH64)) + if (arch.equals("arm64")) { - return ARCH_ARM64; + return "aarch64"; } - if (arch.equals(ARCH_ARM)) + if (arch.equals("armhf") || arch.equals("aarch32")) { - return ARCH_ARMHF; + return "arm"; } return arch; } @@ -155,17 +104,17 @@ private static String getExt() { return ext; } - if (os.equals(OS_LINUX) || os.equals(OS_FREEBSD) || os.equals(OS_SUNOS)) + if (os.equals("linux") || os.equals("freebsd") || os.equals("sunos")) { - return EXT_SO; + return "so"; } - if (os.equals(OS_WINDOWS)) + if (os.equals("win32")) { - return EXT_DLL; + return "dll"; } - if (os.equals(OS_MACOS)) + if (os.equals("darwin")) { - return EXT_DYLIB; + return "dylib"; } throw new LoaderException("Unable to determine the shared library " + "file extension for operating system '" + os From dfffd0521e7de6f2cc15c98ef5cdf7c6a0ff6854 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Wed, 10 Oct 2018 23:33:43 +0200 Subject: [PATCH 26/44] Map armv7l arch to arm binary --- src/main/java/org/usb4java/Loader.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/org/usb4java/Loader.java b/src/main/java/org/usb4java/Loader.java index e6917d0..3706e44 100644 --- a/src/main/java/org/usb4java/Loader.java +++ b/src/main/java/org/usb4java/Loader.java @@ -83,7 +83,7 @@ private static String getArch() { return "aarch64"; } - if (arch.equals("armhf") || arch.equals("aarch32")) + if (arch.equals("armhf") || arch.equals("aarch32") || arch.equals("armv7l")) { return "arm"; } From 7d65b24fd7aee6bd9516ff0e96d9c5906b0c6e62 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Thu, 11 Oct 2018 07:34:42 +0200 Subject: [PATCH 27/44] Add changelog entry --- src/changes/changes.xml | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/changes/changes.xml b/src/changes/changes.xml index 493623d..8ba74dd 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -9,6 +9,12 @@ + + Renamed os and architecture identifiers to the naming conventions of + the JNA project. So the platforms are now named: linux-x86, + linux-x86-64, linux-arm, linux-aarch64, darwin-x86-64, win32-x86 and + win32-x86-64. + Add missing SPEED_SUPER_PLUS constant. From bbd9390f47bfbd76ede242b529a3aecd55794e44 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Fri, 12 Oct 2018 08:43:29 +0200 Subject: [PATCH 28/44] Implement getPollfds and freePollfds --- src/changes/changes.xml | 2 +- src/main/java/org/usb4java/LibUsb.java | 33 ++++-- src/main/java/org/usb4java/Pollfd.java | 111 ++++++++++++++++++ src/main/java/org/usb4java/Pollfds.java | 102 ++++++++++++++++ .../java/org/usb4java/PollfdsIterator.java | 53 +++++++++ .../java/org/usb4java/LibUsbDeviceTest.java | 99 ++++++++++++++++ 6 files changed, 391 insertions(+), 9 deletions(-) create mode 100644 src/main/java/org/usb4java/Pollfd.java create mode 100644 src/main/java/org/usb4java/Pollfds.java create mode 100644 src/main/java/org/usb4java/PollfdsIterator.java diff --git a/src/changes/changes.xml b/src/changes/changes.xml index 8ba74dd..de229a9 100644 --- a/src/changes/changes.xml +++ b/src/changes/changes.xml @@ -19,7 +19,7 @@ Add missing SPEED_SUPER_PLUS constant. - Wrap new libusb functions: setOption, devMemAlloc, devMemFree, interruptEventHandler. + Wrap new libusb functions: setOption, devMemAlloc, devMemFree, interruptEventHandler, getPollfds, freePollfds. Updated to libusb 1.0.22. diff --git a/src/main/java/org/usb4java/LibUsb.java b/src/main/java/org/usb4java/LibUsb.java index c232569..b1ba7a3 100644 --- a/src/main/java/org/usb4java/LibUsb.java +++ b/src/main/java/org/usb4java/LibUsb.java @@ -775,8 +775,6 @@ private LibUsb() * Some options require one or more arguments to be provided. Consult each option's documentation for specific * requirements. * - * Since libusb version 1.0.22, LIBUSB_API_VERSION >= 0x01000106 - * * @param context * The {@link Context} on which to operate. * @param option @@ -796,8 +794,6 @@ public static int setOption(final Context context, final int option) { * Some options require one or more arguments to be provided. Consult each option's documentation for specific * requirements. * - * Since libusb version 1.0.22, LIBUSB_API_VERSION >= 0x01000106 - * * @param context * The {@link Context} on which to operate. * @param option @@ -1335,8 +1331,6 @@ public static native int freeStreams(final DeviceHandle handle, * allocated with this function must be freed with {@link #devMemFree()}. Specifically, this means that the flag * {@link #TRANSFER_FREE_BUFFER} cannot be used to free memory allocated with this function. * - * Since version 1.0.21, LIBUSB_API_VERSION >= 0x01000105 - * * @param handle * A device handle. * @param length @@ -2140,8 +2134,6 @@ public static native int interruptTransfer(final DeviceHandle handle, * This is mainly useful for interrupting a dedicated event handling thread when an application wishes to call * {@link #exit()}. * - * Since version 1.0.21, LIBUSB_API_VERSION >= 0x01000105 - * * @param ctx * The context to operate on, or NULL for the default context. */ @@ -2516,6 +2508,31 @@ static native void setPollfdNotifiersNative(final Context context, */ static native void unsetPollfdNotifiersNative(final Context context); + /** + * Retrieve a list of file descriptors that should be polled by your main loop as libusb event sources. + * + * The returned list should be freed with {@link #freePollfds()} when done. The actual list contents must not be + * touched. + * + * As file descriptors are a Unix-specific concept, this function is not available on Windows and will always + * return NULL. + * + * @param context + * The context to operate on, or NULL for the default context. + * @return A list of libusb_pollfd structures, NULL on error, NULL on platforms where the functionality is not + * available. + */ + public static native Pollfds getPollfds(final Context context); + + /** + * Free a list of {@link Pollfd} structures. + * + * This should be called for all pollfd lists allocated with {@link #getPollfds()}. + * + * It is legal to call this function with a NULL pollfd list. In this case, the function will simply return safely. + */ + public static native void freePollfds(final Pollfds pollfds); + /** * Allocate a libusb transfer without support for isochronous transfers. * diff --git a/src/main/java/org/usb4java/Pollfd.java b/src/main/java/org/usb4java/Pollfd.java new file mode 100644 index 0000000..38dd6e1 --- /dev/null +++ b/src/main/java/org/usb4java/Pollfd.java @@ -0,0 +1,111 @@ +/* + * Copyright 2018 Klaus Reimer + * See LICENSE.md for licensing information. + * + * Based on libusb : + * + * Copyright 2001 Johannes Erdfelt + * Copyright 2007-2009 Daniel Drake + * Copyright 2010-2012 Peter Stuge + * Copyright 2008-2013 Nathan Hjelm + * Copyright 2009-2013 Pete Batard + * Copyright 2009-2013 Ludovic Rousseau + * Copyright 2010-2012 Michael Plante + * Copyright 2011-2013 Hans de Goede + * Copyright 2012-2013 Martin Pieuchot + * Copyright 2012-2013 Toby Gray + */ + +package org.usb4java; + +/** + * File descriptor for polling. + * + * @author Klaus Reimer (k@ailis.de) + */ +public final class Pollfd +{ + /** There is data to read */ + public static final int POLLIN = 1; + + /** Writing now will not block. */ + public static final int POLLOUT = 4; + + /** The native pointer to the pollfd structure. */ + private long pollfdPointer; + + /** + * Package-private constructor to prevent manual instantiation. Structures are + * always created by JNI. + */ + Pollfd() + { + // Empty + } + + /** + * Returns the native pointer to the pollfd structure. + * + * @return The native pointer to the pollfd structure. + */ + public long getPointer() + { + return this.pollfdPointer; + } + + @Override + public int hashCode() + { + final int prime = 31; + int result = 1; + result = (prime * result) + + (int) (this.pollfdPointer ^ (this.pollfdPointer >>> 32)); + return result; + } + + @Override + public boolean equals(final Object obj) + { + if (this == obj) + { + return true; + } + if (obj == null) + { + return false; + } + if (this.getClass() != obj.getClass()) + { + return false; + } + final Pollfd other = (Pollfd) obj; + if (this.pollfdPointer != other.pollfdPointer) + { + return false; + } + return true; + } + + @Override + public String toString() + { + return String.format("libusb pollfd 0x%x", this.pollfdPointer); + } + + /** + * Returns the numeric file descriptor. + * + * @return The numeric file descriptor. + */ + public native byte fd(); + + /** + * Returns the event flags to poll. + * + * {@link #POLLIN} indicates that you should monitor this file descriptor for becoming ready to read from, and + * {@link #POLLOUT} indicates that you should monitor this file descriptor for non-blocking write readiness. + * + * @return The event flags to poll. + */ + public native short events(); +} diff --git a/src/main/java/org/usb4java/Pollfds.java b/src/main/java/org/usb4java/Pollfds.java new file mode 100644 index 0000000..bb1906d --- /dev/null +++ b/src/main/java/org/usb4java/Pollfds.java @@ -0,0 +1,102 @@ +/* + * Copyright 2018 Klaus Reimer + * See LICENSE.md for licensing information. + */ + +package org.usb4java; + +import java.util.Iterator; + +/** + * List of poll file descriptors as returned by {@link LibUsb#getPollfds(Context)}. + * + * @author Klaus Reimer (k@ailis.de) + */ +public final class Pollfds implements Iterable +{ + /** The native pointer to the pollfd array. */ + private long pollfdsPointer; + + /** The number of file descriptors in the list. */ + private int size; + + /** + * Package-private constructor to prevent manual instantiation. Structures are + * always created by JNI. + */ + Pollfds() + { + // Empty + } + + /** + * Returns the native pointer. + * + * @return The native pointer. + */ + public long getPointer() + { + return this.pollfdsPointer; + } + + /** + * Returns the number of poll file descriptors in the list. + * + * @return The number of poll file descriptors in the list. + */ + public int getSize() + { + return this.size; + } + + /** + * Returns the poll file descriptor with the specified index. + * + * @param index + * The index. + * @return The poll file descriptor or null when index is out of bounds. + */ + public native Pollfd get(final int index); + + @Override + public Iterator iterator() + { + return new PollfdsIterator(this); + } + + @Override + public int hashCode() + { + final int prime = 31; + int result = 1; + result = (prime * result) + + (int) (this.pollfdsPointer ^ (this.pollfdsPointer >>> 32)); + return result; + } + + @Override + public boolean equals(final Object obj) + { + if (this == obj) + { + return true; + } + if (obj == null) + { + return false; + } + if (this.getClass() != obj.getClass()) + { + return false; + } + final Pollfds other = (Pollfds) obj; + return this.pollfdsPointer == other.pollfdsPointer; + } + + @Override + public String toString() + { + return String.format("libusb pollfd list 0x%x with size %d", + this.pollfdsPointer, this.size); + } +} diff --git a/src/main/java/org/usb4java/PollfdsIterator.java b/src/main/java/org/usb4java/PollfdsIterator.java new file mode 100644 index 0000000..41a7755 --- /dev/null +++ b/src/main/java/org/usb4java/PollfdsIterator.java @@ -0,0 +1,53 @@ +/* + * Copyright (C) 2018 Klaus Reimer + * See LICENSE.md for licensing information. + */ + +package org.usb4java; + +import java.util.Iterator; +import java.util.NoSuchElementException; + +/** + * Iterator for {@link Pollfds}. + * + * @author Klaus Reimer (k@ailis.de) + */ +final class PollfdsIterator implements Iterator +{ + /** The file descriptor list. */ + private final Pollfds pollfds; + + /** The current index. */ + private int nextIndex; + + /** + * Constructor. + * + * @param pollfds + * The file descriptor list list. + */ + PollfdsIterator(final Pollfds pollfds) + { + this.pollfds = pollfds; + } + + @Override + public boolean hasNext() + { + return this.nextIndex < this.pollfds.getSize(); + } + + @Override + public Pollfd next() + { + if (!hasNext()) throw new NoSuchElementException(); + return this.pollfds.get(this.nextIndex++); + } + + @Override + public void remove() + { + throw new UnsupportedOperationException(); + } +} diff --git a/src/test/java/org/usb4java/LibUsbDeviceTest.java b/src/test/java/org/usb4java/LibUsbDeviceTest.java index 08611fa..43366f1 100644 --- a/src/test/java/org/usb4java/LibUsbDeviceTest.java +++ b/src/test/java/org/usb4java/LibUsbDeviceTest.java @@ -9,8 +9,11 @@ import static org.usb4java.test.UsbAssume.isUsbTestsEnabled; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNotEquals; +import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; +import static org.junit.Assume.assumeFalse; import static org.junit.Assume.assumeNotNull; import java.nio.ByteBuffer; @@ -1212,4 +1215,100 @@ public void testGetAndFreeDeviceListWithDefaultContext() LibUsb.exit(null); } } + + /** + * Tests the {@link LibUsb#getPollfds()} and {@link LibUsb#freePollfds()} methods. + */ + @Test + public void testGetAndFreePollfds() + { + assumeUsbTestsEnabled(); + + final Pollfds pollfds = LibUsb.getPollfds(this.context); + try { + if (System.getProperty("os.name").toLowerCase().contains("windows")) { + assertNull(pollfds); + } else { + assertNotNull(pollfds); + assertTrue("Size must be >= 0", pollfds.getSize() >= 0); + int i = 0; + for (Pollfd pollfd : pollfds) { + assertEquals(pollfds.get(i), pollfd); + assertTrue("File descriptor must be > 0", pollfd.fd() > 0); + assertTrue("Events must be > 0", pollfd.events() > 0); + i++; + } + } + } finally { + LibUsb.freePollfds(pollfds); + } + } + + /** + * Tests the {@link LibUsb#getPollfds()} and {@link LibUsb#freePollfds()} methods with the default context. + */ + @Test + public void testGetAndFreePollfdsWithDefaultContext() + { + assumeUsbTestsEnabled(); + + assertEquals(0, LibUsb.init(null)); + final Pollfds pollfds = LibUsb.getPollfds(null); + try { + if (System.getProperty("os.name").toLowerCase().contains("windows")) { + assertNull(pollfds); + } else { + assertNotNull(pollfds); + assertTrue("Size must be >= 0", pollfds.getSize() >= 0); + int i = 0; + for (Pollfd pollfd : pollfds) { + assertEquals(pollfds.get(i), pollfd); + assertTrue("File descriptor must be > 0", pollfd.fd() > 0); + assertTrue("Events must be > 0", pollfd.events() > 0); + i++; + } + } + } finally { + LibUsb.freePollfds(pollfds); + } + } + + /** + * Ensures that {@link LibUsb#freePollfds()} doesn't throw an error when called with null argument. + */ + @Test + public void testFreePollfdsWithNullArgument() + { + LibUsb.freePollfds(null); + } + + /** + * Ensures that {@link LibUsb#freePollfds()} doesn't crash when called twice and throws an IllegalStateException + * instead. + */ + @Test(expected = IllegalStateException.class) + public void testDoubleFreePollfds() + { + assumeFalse(System.getProperty("os.name").toLowerCase().contains("windows")); + assumeUsbTestsEnabled(); + final Pollfds pollfds = LibUsb.getPollfds(this.context); + LibUsb.freePollfds(pollfds); + LibUsb.freePollfds(pollfds); + } + + /** + * Ensures that accessing Pollfds properties after calling {@link LibUsb#freePollfds()} doesn't crash and + * throws an IllegalStateException instead. + */ + @Test(expected = IllegalStateException.class) + public void testPollfdsAccessAfterFree() + { + assumeFalse(System.getProperty("os.name").toLowerCase().contains("windows")); + assumeUsbTestsEnabled(); + assertEquals(0, LibUsb.init(null)); + final Pollfds pollfds = LibUsb.getPollfds(null); + assertNotNull(pollfds); + LibUsb.freePollfds(pollfds); + assertNotNull(pollfds.get(0)); + } } From 2ece25826fe7c8561ef01a5103ccb1736933ae42 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Fri, 12 Oct 2018 08:48:55 +0200 Subject: [PATCH 29/44] Free USB contexts in tests --- .../java/org/usb4java/LibUsbDeviceTest.java | 52 ++++--- src/test/java/org/usb4java/LibUsbTest.java | 132 +++++++++++------- 2 files changed, 113 insertions(+), 71 deletions(-) diff --git a/src/test/java/org/usb4java/LibUsbDeviceTest.java b/src/test/java/org/usb4java/LibUsbDeviceTest.java index 43366f1..6253ee5 100644 --- a/src/test/java/org/usb4java/LibUsbDeviceTest.java +++ b/src/test/java/org/usb4java/LibUsbDeviceTest.java @@ -1253,23 +1253,30 @@ public void testGetAndFreePollfdsWithDefaultContext() assumeUsbTestsEnabled(); assertEquals(0, LibUsb.init(null)); - final Pollfds pollfds = LibUsb.getPollfds(null); - try { - if (System.getProperty("os.name").toLowerCase().contains("windows")) { - assertNull(pollfds); - } else { - assertNotNull(pollfds); - assertTrue("Size must be >= 0", pollfds.getSize() >= 0); - int i = 0; - for (Pollfd pollfd : pollfds) { - assertEquals(pollfds.get(i), pollfd); - assertTrue("File descriptor must be > 0", pollfd.fd() > 0); - assertTrue("Events must be > 0", pollfd.events() > 0); - i++; + try + { + final Pollfds pollfds = LibUsb.getPollfds(null); + try { + if (System.getProperty("os.name").toLowerCase().contains("windows")) { + assertNull(pollfds); + } else { + assertNotNull(pollfds); + assertTrue("Size must be >= 0", pollfds.getSize() >= 0); + int i = 0; + for (Pollfd pollfd : pollfds) { + assertEquals(pollfds.get(i), pollfd); + assertTrue("File descriptor must be > 0", pollfd.fd() > 0); + assertTrue("Events must be > 0", pollfd.events() > 0); + i++; + } } + } finally { + LibUsb.freePollfds(pollfds); } - } finally { - LibUsb.freePollfds(pollfds); + } + finally + { + LibUsb.exit(null); } } @@ -1306,9 +1313,16 @@ public void testPollfdsAccessAfterFree() assumeFalse(System.getProperty("os.name").toLowerCase().contains("windows")); assumeUsbTestsEnabled(); assertEquals(0, LibUsb.init(null)); - final Pollfds pollfds = LibUsb.getPollfds(null); - assertNotNull(pollfds); - LibUsb.freePollfds(pollfds); - assertNotNull(pollfds.get(0)); + try + { + final Pollfds pollfds = LibUsb.getPollfds(null); + assertNotNull(pollfds); + LibUsb.freePollfds(pollfds); + assertNotNull(pollfds.get(0)); + } + finally + { + LibUsb.exit(null); + } } } diff --git a/src/test/java/org/usb4java/LibUsbTest.java b/src/test/java/org/usb4java/LibUsbTest.java index 27fa5fc..a798a33 100644 --- a/src/test/java/org/usb4java/LibUsbTest.java +++ b/src/test/java/org/usb4java/LibUsbTest.java @@ -201,16 +201,23 @@ public void testSetOption() assumeUsbTestsEnabled(); final Context context = new Context(); assertEquals(LibUsb.SUCCESS, LibUsb.init(context)); - if (System.getProperty("os.name").toLowerCase().contains("windows")) { - // On Windows this is either a success when USBDK is found or ERROR_NOT_FOUND when not - final int result = LibUsb.setOption(context, LibUsb.OPTION_USE_USBDK); - assertTrue(result == LibUsb.SUCCESS || result == LibUsb.ERROR_NOT_FOUND); - } else { - // On other operating systems it is always ERROR_NOT_SUPPORTED - assertEquals(LibUsb.ERROR_NOT_SUPPORTED, LibUsb.setOption(context, LibUsb.OPTION_USE_USBDK)); + try + { + if (System.getProperty("os.name").toLowerCase().contains("windows")) { + // On Windows this is either a success when USBDK is found or ERROR_NOT_FOUND when not + final int result = LibUsb.setOption(context, LibUsb.OPTION_USE_USBDK); + assertTrue(result == LibUsb.SUCCESS || result == LibUsb.ERROR_NOT_FOUND); + } else { + // On other operating systems it is always ERROR_NOT_SUPPORTED + assertEquals(LibUsb.ERROR_NOT_SUPPORTED, LibUsb.setOption(context, LibUsb.OPTION_USE_USBDK)); + } + assertEquals(LibUsb.SUCCESS, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, LibUsb.LOG_LEVEL_NONE)); + assertEquals(LibUsb.SUCCESS, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, LibUsb.LOG_LEVEL_DEBUG)); + } + finally + { + LibUsb.exit(context); } - assertEquals(LibUsb.SUCCESS, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, LibUsb.LOG_LEVEL_NONE)); - assertEquals(LibUsb.SUCCESS, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, LibUsb.LOG_LEVEL_DEBUG)); } /** @@ -222,8 +229,15 @@ public void testSetOptionWithInvalidParameters() assumeUsbTestsEnabled(); final Context context = new Context(); assertEquals(LibUsb.SUCCESS, LibUsb.init(context)); - assertEquals(LibUsb.ERROR_INVALID_PARAM, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, 234)); - assertEquals(LibUsb.ERROR_INVALID_PARAM, LibUsb.setOption(context, 123)); + try + { + assertEquals(LibUsb.ERROR_INVALID_PARAM, LibUsb.setOption(context, LibUsb.OPTION_LOG_LEVEL, 234)); + assertEquals(LibUsb.ERROR_INVALID_PARAM, LibUsb.setOption(context, 123)); + } + finally + { + LibUsb.exit(context); + } } /** @@ -1318,46 +1332,53 @@ public void testPollFdNotifiers() final PollfdListenerMock listener = new PollfdListenerMock(); final Context context = new Context(); LibUsb.init(context); - LibUsb.setPollfdNotifiers(context, listener, "test"); - - FileDescriptor fd = new FileDescriptor(); - LibUsb.triggerPollfdAdded(fd, 53, context.getPointer()); - assertEquals(53, listener.addedEvents); - assertSame(fd, listener.addedFd); - assertSame("test", listener.addedUserData); - assertNull(listener.removedFd); - assertNull(listener.removedUserData); - - listener.reset(); - - fd = new FileDescriptor(); - LibUsb.triggerPollfdRemoved(fd, context.getPointer()); - assertEquals(0, listener.addedEvents); - assertNull(listener.addedFd); - assertNull(listener.addedUserData); - assertSame(fd, listener.removedFd); - assertSame("test", listener.removedUserData); - - LibUsb.setPollfdNotifiers(context, null, null); - listener.reset(); - - fd = new FileDescriptor(); - LibUsb.triggerPollfdAdded(fd, 53, context.getPointer()); - assertEquals(0, listener.addedEvents); - assertNull(listener.addedFd); - assertNull(listener.addedUserData); - assertNull(listener.removedFd); - assertNull(listener.removedUserData); - - listener.reset(); - - fd = new FileDescriptor(); - LibUsb.triggerPollfdRemoved(fd, context.getPointer()); - assertEquals(0, listener.addedEvents); - assertNull(listener.addedFd); - assertNull(listener.addedUserData); - assertNull(listener.removedFd); - assertNull(listener.removedUserData); + try + { + LibUsb.setPollfdNotifiers(context, listener, "test"); + + FileDescriptor fd = new FileDescriptor(); + LibUsb.triggerPollfdAdded(fd, 53, context.getPointer()); + assertEquals(53, listener.addedEvents); + assertSame(fd, listener.addedFd); + assertSame("test", listener.addedUserData); + assertNull(listener.removedFd); + assertNull(listener.removedUserData); + + listener.reset(); + + fd = new FileDescriptor(); + LibUsb.triggerPollfdRemoved(fd, context.getPointer()); + assertEquals(0, listener.addedEvents); + assertNull(listener.addedFd); + assertNull(listener.addedUserData); + assertSame(fd, listener.removedFd); + assertSame("test", listener.removedUserData); + + LibUsb.setPollfdNotifiers(context, null, null); + listener.reset(); + + fd = new FileDescriptor(); + LibUsb.triggerPollfdAdded(fd, 53, context.getPointer()); + assertEquals(0, listener.addedEvents); + assertNull(listener.addedFd); + assertNull(listener.addedUserData); + assertNull(listener.removedFd); + assertNull(listener.removedUserData); + + listener.reset(); + + fd = new FileDescriptor(); + LibUsb.triggerPollfdRemoved(fd, context.getPointer()); + assertEquals(0, listener.addedEvents); + assertNull(listener.addedFd); + assertNull(listener.addedUserData); + assertNull(listener.removedFd); + assertNull(listener.removedUserData); + } + finally + { + LibUsb.exit(context); + } } /** @@ -1369,6 +1390,13 @@ public void testInterruptEventHandler() assumeUsbTestsEnabled(); final Context context = new Context(); assertEquals(LibUsb.SUCCESS, LibUsb.init(context)); - LibUsb.interruptEventHandler(context); + try + { + LibUsb.interruptEventHandler(context); + } + finally + { + LibUsb.exit(context); + } } } From 5f3cad266a625cecd40d85427aea3f3952a40e9d Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 12:21:25 +0200 Subject: [PATCH 30/44] Switch from BZ2 to XZ compression --- src/main/assembly/tarball.xml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/assembly/tarball.xml b/src/main/assembly/tarball.xml index 9b1d4b9..35bb930 100644 --- a/src/main/assembly/tarball.xml +++ b/src/main/assembly/tarball.xml @@ -4,7 +4,7 @@ xsi:schemaLocation="http://maven.apache.org/plugins/maven-assembly-plugin/assembly/1.1.2 http://maven.apache.org/xsd/assembly-1.1.2.xsd"> tarball - tar.bz2 + tar.xz @@ -30,9 +30,9 @@ - lib + lib false runtime - + From 5249c172f98b7307169116523c42ec43ccc4b32a Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 12:21:37 +0200 Subject: [PATCH 31/44] Fix javadoc links --- src/main/java/org/usb4java/LibUsb.java | 21 +++++++++++---------- 1 file changed, 11 insertions(+), 10 deletions(-) diff --git a/src/main/java/org/usb4java/LibUsb.java b/src/main/java/org/usb4java/LibUsb.java index b1ba7a3..6cebb61 100644 --- a/src/main/java/org/usb4java/LibUsb.java +++ b/src/main/java/org/usb4java/LibUsb.java @@ -89,7 +89,7 @@ public final class LibUsb /** * Use the UsbDk backend for a specific context, if available. * - * This option should be set immediately after calling {@link #init()}, otherwise + * This option should be set immediately after calling {@link #init(Context)}, otherwise * unspecified behavior may occur. * * Only valid on Windows. @@ -763,7 +763,7 @@ private LibUsb() * @param level * The log level to set. * - * @deprecated Use {@link #setOption()} instead using the {@link #OPTION_LOG_LEVEL} option. + * @deprecated Use {@link #setOption(Context, int, int)} instead using the {@link #OPTION_LOG_LEVEL} option. */ public static native void setDebug(final Context context, final int level); @@ -1328,8 +1328,9 @@ public static native int freeStreams(final DeviceHandle handle, * is in progress, although it is legal to have several transfers going on within the same memory block. * * Will return NULL on failure. Many systems do not support such zerocopy and will always return NULL. Memory - * allocated with this function must be freed with {@link #devMemFree()}. Specifically, this means that the flag - * {@link #TRANSFER_FREE_BUFFER} cannot be used to free memory allocated with this function. + * allocated with this function must be freed with {@link #devMemFree(DeviceHandle, ByteBuffer, int)}. + * Specifically, this means that the flag {@link #TRANSFER_FREE_BUFFER} cannot be used to free memory + * allocated with this function. * * @param handle * A device handle. @@ -1340,7 +1341,7 @@ public static native int freeStreams(final DeviceHandle handle, public static native ByteBuffer devMemAlloc(final DeviceHandle handle, final int length); /** - * Free device memory allocated with {@link #devMemAlloc()}. + * Free device memory allocated with {@link #devMemAlloc(DeviceHandle, int)}. * * @param handle * A device handle. @@ -1350,7 +1351,7 @@ public static native int freeStreams(final DeviceHandle handle, * The size of the previously allocated memory. * @return {@link #SUCCESS}, or a LIBUSB_ERROR code on failure. */ - public static native int devMemFree(final DeviceHandle handle, final ByteBuffer buffer, final int length); + public static native int devMemFree(final DeviceHandle handle, final ByteBuffer buffer, final int size); /** * Determine if a kernel driver is active on an interface. @@ -2132,9 +2133,9 @@ public static native int interruptTransfer(final DeviceHandle handle, * Interrupt any active thread that is handling events. * * This is mainly useful for interrupting a dedicated event handling thread when an application wishes to call - * {@link #exit()}. + * {@link #exit(Context)}. * - * @param ctx + * @param context * The context to operate on, or NULL for the default context. */ public static native void interruptEventHandler(final Context context); @@ -2511,7 +2512,7 @@ static native void setPollfdNotifiersNative(final Context context, /** * Retrieve a list of file descriptors that should be polled by your main loop as libusb event sources. * - * The returned list should be freed with {@link #freePollfds()} when done. The actual list contents must not be + * The returned list should be freed with {@link #freePollfds(Pollfds)} when done. The actual list contents must not be * touched. * * As file descriptors are a Unix-specific concept, this function is not available on Windows and will always @@ -2527,7 +2528,7 @@ static native void setPollfdNotifiersNative(final Context context, /** * Free a list of {@link Pollfd} structures. * - * This should be called for all pollfd lists allocated with {@link #getPollfds()}. + * This should be called for all pollfd lists allocated with {@link #getPollfds(Context)}. * * It is legal to call this function with a NULL pollfd list. In this case, the function will simply return safely. */ From df699d2612c0215a764f07bedc62372794b450a2 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 12:22:03 +0200 Subject: [PATCH 32/44] Improve documentation --- src/site/apt/configuration.apt.vm | 25 ++++++++---- src/site/apt/faq.apt.vm | 39 +++++++++--------- src/site/apt/nativelibs.apt.vm | 67 +++++++++++++++++-------------- src/site/apt/quickstart/index.apt | 23 +++++------ src/site/xdoc/index.xml.vm | 40 +++++++++--------- 5 files changed, 103 insertions(+), 91 deletions(-) diff --git a/src/site/apt/configuration.apt.vm b/src/site/apt/configuration.apt.vm index ea46ed9..7d6ef54 100644 --- a/src/site/apt/configuration.apt.vm +++ b/src/site/apt/configuration.apt.vm @@ -1,7 +1,7 @@ ----------------------------------------------------------------------------- Configuration ----------------------------------------------------------------------------- - + Configuration The configuration options explained here are only valid for the javax-usb @@ -15,21 +15,21 @@ Configuration implementation you have to put the following property into the file which must be located in the root of your classpath: - + +----+ javax.usb.services = org.usb4java.javax.Services -+----+ ++----+ can be configured by adding more properties to this file as described in the following sections. - + * Communication timeout The default USB communication timeout of is 2500 milliseconds. To change this to 250 milliseconds for example add this to the properties - file: - + file: + +----+ org.usb4java.javax.timeout = 250 +----+ @@ -52,4 +52,15 @@ org.usb4java.javax.scanInterval = 1000 +----+ ((org.usb4java.javax.Services) UsbHostManager.getUsbServices()).scan(); +----+ - \ No newline at end of file + + +* Use USBDK + + If you want to use {{{https://github.com/daynix/UsbDk}USBDK}} on Windows + then you have to enable the feature with the following entry: + ++----+ +org.usb4java.javax.useUSBDK = true ++----+ + + This setting is ignored on other platforms. diff --git a/src/site/apt/faq.apt.vm b/src/site/apt/faq.apt.vm index 581bfff..5bd958e 100644 --- a/src/site/apt/faq.apt.vm +++ b/src/site/apt/faq.apt.vm @@ -1,15 +1,15 @@ ----------------------------------------------------------------------------- FAQ ----------------------------------------------------------------------------- - + Frequently asked questions If you have a question which is not answered here please ask the {{{mailto:usb4java@googlegroups.com}usb4java mailing list}} ({{{http://groups.google.com/group/usb4java}Google group}}). - You can subscribe to it via email by sending a mail to + You can subscribe to it via email by sending a mail to {{{mailto:usb4java+subscribe@googlegroups.com}usb4java+subscribe@googlegroups.com}}. - + * I can't open my USB device on Linux. Why? On Linux you need write permissions on the device file of the USB device @@ -20,49 +20,48 @@ Frequently asked questions with content like this: ---- - SUBSYSTEM=="usb",ATTR{idVendor}=="89ab",ATTR{idProduct}=="4567",MODE="0660",GROUP="wheel" + SUBSYSTEM=="usb",ATTR{idVendor}=="89ab",ATTR{idProduct}=="4567",MODE="0660",GROUP="plugdev" ---- This means that whenever a USB device with vendor id <0x89ab> and product id <0x4567> is attached then the group is permitted to write to the device. So make sure your user is in that group (or use a different group). - + If your device uses a shared vendor/product id then you might want to filter for the manufacturer and product name. This can be done by checking the ATTR properties and . - + To activate this new configuration you may need to re-attach the USB device or run the command <<>>. * I can't open my USB device on Windows. Why? On Windows you need to create a driver for your USB device. Read the - {{{https://github.com/libusb/libusb/wiki/Windows#wiki-How_to_use_libusb_on_Windows}How to use libusb on Windows}} + {{{https://github.com/libusb/libusb/wiki/Windows#wiki-How_to_use_libusb_on_Windows}How to use libusb on Windows}} article from the {{{http://libusb.info}libusb project}} for more information. * My program crashes. What can I do? - If the program crashes with a Java stack trace then it is most likely a - problem in your own program. If you can't find it you may find some help on - the {{{./mail-lists.html}mailinglist}}. - + If the program crashes with a Java stack trace then it is most likely a + problem in your own program. If you can't find it you may find some help on + the {{{./mail-lists.html}mailinglist}}. + If the JVM crashes the hard way because of a segfault in the native code then - it is more likely a problem of usb4java or libusb and you should file a + it is more likely a problem of usb4java or libusb and you should file a {{{./issue-tracking.html}bugreport}} with as much information as possible (Full stack trace, full crash log, example code how to reproduce the crash). - + If usb4java crashes on Windows then please first of all make sure you have created a proper device driver as explained in the previous FAQ entry. Also consider creating a new up-to-date device driver with the latest Zadig tool. - + If you have experience in C programming then it would be very helpful when you could try to reproduce the problem in C by directly using libusb. If - this works but the same USB communication doesn't work with usb4java then it - would be nice if you could give us your C source and Java source so we can + this works but the same USB communication doesn't work with usb4java then it + would be nice if you could give us your C source and Java source so we can track down the difference which causes the crash. If the C program also crashes then your problem is located in libusb and not in usb4java and you - should consult the libusb mailinglist or bug tracker instead. Never report a - problem in the libusb bug tracker or the libusb mailing list if you - can't reproduce the problem with a native C program! - \ No newline at end of file + should consult the libusb mailinglist or bug tracker instead. Never report a + problem in the libusb bug tracker or the libusb mailing list if you + can't reproduce the problem with a native C program! diff --git a/src/site/apt/nativelibs.apt.vm b/src/site/apt/nativelibs.apt.vm index d8399b3..862aa7c 100644 --- a/src/site/apt/nativelibs.apt.vm +++ b/src/site/apt/nativelibs.apt.vm @@ -1,41 +1,41 @@ ----------------------------------------------------------------------------- Native libraries ----------------------------------------------------------------------------- - + Library loading The native libraries for all supported platforms are provided as JAR files which you can simply reference in your classpath. usb4java automatically determines on startup which libraries are needed for the current platform - and extracts them to a temporary directory and loads them from there. - This makes it easy to use usb4java because you just need to put the JARs + and extracts them to a temporary directory and loads them from there. + This makes it easy to use usb4java because you just need to put the JARs into your classpath. No need to fiddle around with or environment variables like or . - + usb4java only extracts the files into a temporary directory when they are inside a JAR file. So if you prefer direct loading without extracting to a temporary directory then you may want to distribute the files in extracted form. Just make sure your classpath includes the directory where you have extracted the JARs. Here is an example application layout for this scenario: - + +-----------------------------------------------------------------------------+ natives/ org/usb4java/ - linux-x86/libusb4java.so - windows-x86/libusb4java.dll - osx-x86/libusb4java.dylib + linux-x86-64/libusb4java.so + win32-x86-64/libusb4java.dll + darwin-x86-64/libusb4java.dylib lib/ usb4java.jar commons-lang3.jar myapp.jar myapp.sh -+-----------------------------------------------------------------------------+ ++-----------------------------------------------------------------------------+ To make this work just make sure to put the folder into your - classpath. + classpath. + - Unsupported platforms When you use usb4java on a platform which is not directly supported by @@ -46,7 +46,7 @@ Native library not found in classpath: /org/usb4java/freebsd-x86/libusb4java.so +----+ +----+ -Unable to determine the shared library file extension for operating system +Unable to determine the shared library file extension for operating system 'strangeos'. Please specify Java parameter -Dusb4java.libext.strangeos= +----+ @@ -54,12 +54,12 @@ Unable to determine the shared library file extension for operating system is completely unknown to the usb4java authors and usb4java does not know the file extension of shared libraries on this platform. You can fix this by specifying a Java parameter like this (As explained in the exception): - + +----+ -Dusb4java.libext.strangeos=so +----+ - After this you will most likely get the other exception, which means that + After this you will most likely get the other exception, which means that there is no native JNI wrapper present for this platform. Your only chance here is to compile this wrapper yourself. I can't predict how this works on really strange platforms but chances are high that your platform is @@ -68,48 +68,53 @@ Unable to determine the shared library file extension for operating system 1. Install a Java JDK ({{{http://openjdk.java.net/}OpenJDK}} for example). Make sure the environment variable is pointing to the directory where you have installed the JDK. - + 2. Install the {{{http://libusb.info/}libusb}} development files. - + 3. Install {{{http://git-scm.com/}Git}}. - + 4. Clone the {{{https://github.com/usb4java/libusb4java/}libusb4java source code repository}} with Git: - + +---- $ git clone git://github.com/usb4java/libusb4java.git +---- 5. Enter the cloned libusb4java directory: - + +---- $ cd libusb4java +---- - 6. Compile the native library: - + 6. Create a build output directory and enter it: + ++--- +$ mkdir build +$ cd build ++--- + + 7. Compile the native library: + ++---- +$ cmake .. -DCMAKE_INSTALL_PREFIX="" +$ make install/strip DESTDIR=/tmp +---- -$ ./autogen.sh -$ ./configure --prefix=/ -$ make install-strip DESTDIR=/tmp -+---- - 8. When compilation was successful then the native library can be found in + 8. When compilation was successful then the native library can be found in the directory . The file name depends on your operating system. Make sure you rename it to (Or whatever file extension - your platform uses) and copy this file into the directory + your platform uses) and copy this file into the directory in your classpath where is the name of your operating system and is your CPU architecture (Both must match the names mentioned in the exception thrown by usb4java.) - - If you can't use the GNU compiler or the autotools then you are on your own. + + If you can't use the GNU compiler or cmake then you are on your own. If you have some experience with compiling JNI libraries then I guess this won't be hard for you. There are only a couple of source files in the sub folder. You could write a new simple Makefile or whatever is needed on your platform. - If you have problems then please consult the + If you have problems then please consult the {{{mailto:usb4java@googlegroups.com}usb4java mailing list}} ({{{http://groups.google.com/group/usb4java}Google group}}). You can subscribe to it via email by sending a mail to {{{mailto:usb4java+subscribe@googlegroups.com}usb4java+subscribe@googlegroups.com}}. - \ No newline at end of file diff --git a/src/site/apt/quickstart/index.apt b/src/site/apt/quickstart/index.apt index f6a36cc..302293a 100644 --- a/src/site/apt/quickstart/index.apt +++ b/src/site/apt/quickstart/index.apt @@ -7,14 +7,14 @@ Quick start * Choose an API usb4java provides two different APIs you can choose from: - + * {{{./libusb.html}The low-level (libusb) API}} - + * {{{./javax-usb.html}The high-level (javax-usb) API}} - + [] - - The low-level API closely follows the C API of the + + The low-level API closely follows the C API of the {{{http://libusb.info/}libusb}} project. This API has the advantage that it provides the same functionality as libusb does. And if you know the C API of libusb then you will most likely feel right at home when using this API @@ -22,16 +22,13 @@ Quick start Java. The disadvantage is that you will have a hard time changing your code when you later switch to a different Java USB library. And as a pure Java developer you may dislike the API because it is too low-level (For - example most methods return error codes instead of throwing exceptions). + example most methods return error codes instead of throwing exceptions). - The high-level API simply implements the + The high-level API simply implements the {{{http://javax-usb.sourceforge.net/}javax-usb (JSR80) API}}. One advantage of this API is that it is implementation-independent. So it is easy to switch to a different javax-usb implementation later without changing your code. Another advantage is that this API is object oriented and is much - easier to use for Java developers. The disadvantage is that the javax-usb - specification is pretty old and may lack support for some newer USB - techniques provided by the low-level API. - - - \ No newline at end of file + easier to use for Java developers. The disadvantage is that the javax-usb + specification is very old (maybe even abandoned) and may lack support for + some newer USB techniques provided by the low-level API. diff --git a/src/site/xdoc/index.xml.vm b/src/site/xdoc/index.xml.vm index 090da5c..d266755 100644 --- a/src/site/xdoc/index.xml.vm +++ b/src/site/xdoc/index.xml.vm @@ -14,34 +14,34 @@ through the usb4java-javax extension.

- Supported platforms are Linux (x86 32/64 bit, ARM 32 bit), - OS X (x86 32/64 bit) and + Supported platforms are Linux (x86 32/64 bit, ARM 32/64 bit), + OS X (x86 64 bit) and Windows (x86 32/64 bit). But other platforms may work - as well (as long as they have at least Java 6 and are supported by + as well (as long as they have at least Java 6 and are supported by libusb) by compiling the JNI library manually.

- +

- When you are using Maven then you can add the necessary dependencies + When you are using Maven then you can add the necessary dependencies like this:

<-- For using just usb4java without javax-usb -->
@@ -62,13 +62,13 @@
   </dependency>
 </dependencies>
- +

- Copyright (C) 2011 Klaus Reimer, k@ailis.de
+ Copyright (C) 2011 Klaus Reimer, k@ailis.de
Copyright (C) 2013 Luca Longinotti, l@longi.li

- +

Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal @@ -91,30 +91,30 @@ THE SOFTWARE.

- +

- Read the quick start guide and the + Read the quick start guide and the FAQ. There are also some low-level (libusb) examples - and + and high-level (javax-usb) examples available.

- +

- For questions and discussions please use the - usb4java mailing list + For questions and discussions please use the + usb4java mailing list (Google group). - You can subscribe to it via email by sending a mail to + You can subscribe to it via email by sending a mail to usb4java+subscribe@googlegroups.com.

-

+

If you have found a bug in the software or this web site (even if it's just a typo) then please create - an issue on GitHub. + an issue on GitHub.

From 091b993be59f886c5143b23602079e4ca42de4f3 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 13:13:11 +0200 Subject: [PATCH 33/44] Update issue templates --- .github/ISSUE_TEMPLATE/bug_report.md | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) create mode 100644 .github/ISSUE_TEMPLATE/bug_report.md diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md new file mode 100644 index 0000000..9c380ca --- /dev/null +++ b/.github/ISSUE_TEMPLATE/bug_report.md @@ -0,0 +1,19 @@ +--- +name: Bug report +about: Create a report to help us improve + +--- + +**Environment:** + - OS: [e.g. Ubuntu 18.10 or Windows 10] + - Java version [e.g. Oracle Java 8] + - usb4java version [e.g. 1.3.0] + +**Bug description** +A clear and concise description of what the bug is. + +**Reproduction** +Java code example showing how to reproduce the error. + +**Expected behavior** +A clear and concise description of what you expected to happen. From 859e96f5a5a62c73d9bffe29b67c0ec8350d719b Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 13:40:16 +0200 Subject: [PATCH 34/44] Use github for release artifacts --- pom.xml | 4 ---- src/site/xdoc/index.xml.vm | 16 +++++----------- 2 files changed, 5 insertions(+), 15 deletions(-) diff --git a/pom.xml b/pom.xml index ecb357d..27893bd 100644 --- a/pom.xml +++ b/pom.xml @@ -60,10 +60,6 @@ UTF-8 - http://nexus.ailis.de/content/groups/public/org/usb4java/${project.artifactId} - - ${repoBaseUrl}/${project.version}/${project.artifactId}-${project.version} - ${repoBaseUrl}-javax/${usb4javaJavaxVersion}/${project.artifactId}-javax-${usb4javaJavaxVersion} 1.3.0-SNAPSHOT 1.3.0-SNAPSHOT diff --git a/src/site/xdoc/index.xml.vm b/src/site/xdoc/index.xml.vm index d266755..8e497a2 100644 --- a/src/site/xdoc/index.xml.vm +++ b/src/site/xdoc/index.xml.vm @@ -25,21 +25,15 @@
+
+ +

When you are using Maven then you can add the necessary dependencies like this: From 7562f65dab939396472b04cdeccc6eeab41e899c Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 17:35:15 +0200 Subject: [PATCH 35/44] Switch to Sonatype OSS repo --- pom.xml | 27 +++++---------------------- 1 file changed, 5 insertions(+), 22 deletions(-) diff --git a/pom.xml b/pom.xml index 27893bd..3817ef2 100644 --- a/pom.xml +++ b/pom.xml @@ -76,11 +76,6 @@ https://github.com/usb4java/${project.artifactId}/issues - - Jenkins - https://ci.ailis.de/job/${project.artifactId}/ - - 3.0.5 @@ -175,7 +170,7 @@ maven-assembly-plugin 3.1.0 - true + false false src/main/assembly/tarball.xml @@ -259,9 +254,10 @@ - ailis - Ailis Maven Repository - http://nexus.ailis.de/content/groups/public/ + sonatype-snapshots + Sonatype Snapshot Repository + https://oss.sonatype.org/content/repositories/snapshots + true @@ -270,7 +266,6 @@ project-website file://${project.basedir}/../${project.artifactId}-site/ - - - ailis-releases - Ailis Maven Releases - http://nexus.ailis.de/content/repositories/releases - - - ailis-snapshots - Ailis Maven Snapshots - http://nexus.ailis.de/content/repositories/snapshots - - From 4932de809145463c8a57238e27030619878c4355 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 18:02:55 +0200 Subject: [PATCH 36/44] Use libusb4java release 1.3.0 --- pom.xml | 11 +++++++++-- src/site/xdoc/index.xml.vm | 2 +- 2 files changed, 10 insertions(+), 3 deletions(-) diff --git a/pom.xml b/pom.xml index 3817ef2..0a02173 100644 --- a/pom.xml +++ b/pom.xml @@ -60,8 +60,7 @@ UTF-8 - 1.3.0-SNAPSHOT - 1.3.0-SNAPSHOT + 1.3.0 @@ -253,10 +252,18 @@ --> + + sonatype-releases + Sonatype Snapshot Repository + https://oss.sonatype.org/content/repositories/releases + true + false + sonatype-snapshots Sonatype Snapshot Repository https://oss.sonatype.org/content/repositories/snapshots + false true diff --git a/src/site/xdoc/index.xml.vm b/src/site/xdoc/index.xml.vm index 8e497a2..a212c30 100644 --- a/src/site/xdoc/index.xml.vm +++ b/src/site/xdoc/index.xml.vm @@ -52,7 +52,7 @@ <dependency> <groupId>${project.groupId}</groupId> <artifactId>${project.artifactId}-javax</artifactId> - <version>${usb4javaJavaxVersion}</version> + <version>${project.version}</version> </dependency> </dependencies>

From ab7c90da1c5799601d746dd8be7ef7c7c9aaa82e Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 18:09:57 +0200 Subject: [PATCH 37/44] Enable artifact signing --- pom.xml | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/pom.xml b/pom.xml index 0a02173..5f12a7a 100644 --- a/pom.xml +++ b/pom.xml @@ -217,10 +217,19 @@ maven-jar-plugin 3.1.0
+ + org.apache.maven.plugins + maven-source-plugin + 3.0.1 + + + org.apache.maven.plugins + maven-javadoc-plugin + 3.0.1 + - From 73e7b7a1785141ff3766dabce2156320ef894e04 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 18:24:06 +0200 Subject: [PATCH 38/44] Remove tag --- pom.xml | 1 - 1 file changed, 1 deletion(-) diff --git a/pom.xml b/pom.xml index 5f12a7a..1bbdb4e 100644 --- a/pom.xml +++ b/pom.xml @@ -67,7 +67,6 @@ scm:git:git://github.com/usb4java/${project.artifactId}.git scm:git:ssh://git@github.com/usb4java/${project.artifactId}.git http://github.com/usb4java/${project.artifactId} - HEAD
From e251a1009fad3f8bda67070d78a03ff9339e636c Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 18:28:08 +0200 Subject: [PATCH 39/44] Pin release plugin version --- pom.xml | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/pom.xml b/pom.xml index 1bbdb4e..b059e85 100644 --- a/pom.xml +++ b/pom.xml @@ -226,6 +226,11 @@ maven-javadoc-plugin 3.0.1
+ + org.apache.maven.plugins + maven-release-plugin + 2.5.3 + From eb9284d319959489de3736c7cc9951b0087d145a Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 18:28:36 +0200 Subject: [PATCH 40/44] [maven-release-plugin] prepare release usb4java-1.3.0 --- pom.xml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index b059e85..a62e257 100644 --- a/pom.xml +++ b/pom.xml @@ -6,7 +6,7 @@ usb4java jar usb4java - 1.3.0-SNAPSHOT + 1.3.0 http://usb4java.org/ USB library for Java based on libusb and implementing javax-usb (JSR-80). @@ -67,6 +67,7 @@ scm:git:git://github.com/usb4java/${project.artifactId}.git scm:git:ssh://git@github.com/usb4java/${project.artifactId}.git http://github.com/usb4java/${project.artifactId} + usb4java-1.3.0 From 17423dfbe12b9cb7dfac95b32eed369672eabfd2 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 18:28:44 +0200 Subject: [PATCH 41/44] [maven-release-plugin] prepare for next development iteration --- pom.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pom.xml b/pom.xml index a62e257..6b8122b 100644 --- a/pom.xml +++ b/pom.xml @@ -6,7 +6,7 @@ usb4java jar usb4java - 1.3.0 + 1.3.1-SNAPSHOT http://usb4java.org/ USB library for Java based on libusb and implementing javax-usb (JSR-80). @@ -67,7 +67,7 @@ scm:git:git://github.com/usb4java/${project.artifactId}.git scm:git:ssh://git@github.com/usb4java/${project.artifactId}.git http://github.com/usb4java/${project.artifactId} - usb4java-1.3.0 + HEAD From 73d4a1a44fe39229dbcb402158427e57a7448580 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Sun, 21 Oct 2018 23:36:04 +0200 Subject: [PATCH 42/44] Use libusb4java snapshot version --- pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index 6b8122b..3e169f6 100644 --- a/pom.xml +++ b/pom.xml @@ -60,7 +60,7 @@ UTF-8 - 1.3.0 + 1.3.1-SNAPSHOT From fa52d0d5483a9d9cbcd23a8be69b785e358b6024 Mon Sep 17 00:00:00 2001 From: Klaus Reimer Date: Fri, 26 Oct 2018 07:55:56 +0200 Subject: [PATCH 43/44] Fix wrong group name --- src/site/apt/faq.apt.vm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/site/apt/faq.apt.vm b/src/site/apt/faq.apt.vm index 5bd958e..620d3d7 100644 --- a/src/site/apt/faq.apt.vm +++ b/src/site/apt/faq.apt.vm @@ -24,7 +24,7 @@ Frequently asked questions ---- This means that whenever a USB device with vendor id <0x89ab> and product id - <0x4567> is attached then the group is permitted to + <0x4567> is attached then the group is permitted to write to the device. So make sure your user is in that group (or use a different group). From 3e680448f3d9bb08d0ce86f1c9b82c12f7e32b4e Mon Sep 17 00:00:00 2001 From: Jesse Pavel Date: Tue, 18 Aug 2020 16:18:13 -0400 Subject: [PATCH 44/44] Allow specifying library name through system property --- src/main/java/org/usb4java/Loader.java | 25 +++++++++++++++++++------ 1 file changed, 19 insertions(+), 6 deletions(-) diff --git a/src/main/java/org/usb4java/Loader.java b/src/main/java/org/usb4java/Loader.java index 3706e44..8d8339a 100644 --- a/src/main/java/org/usb4java/Loader.java +++ b/src/main/java/org/usb4java/Loader.java @@ -300,6 +300,11 @@ private static String extractLibrary(final String platform, * times. Duplicate calls are ignored. This method is automatically called * when the {@link LibUsb} class is loaded. When you need to do it earlier * (To catch exceptions for example) then simply call this method manually. + *

+ * If the system property org.usb4java.LibraryName is defined, then + * instead of going through the classpath looking for the appropriate DLL, + * extracting it, etc., we simply call {@link System#loadLibrary}, passing + * in the value of the property. * * @throws LoaderException * When loading the native wrapper libraries failed. @@ -313,13 +318,21 @@ public static synchronized void load() } loaded = true; - final String platform = getPlatform(); - final String lib = getLibName(); - final String extraLib = getExtraLibName(); - if (extraLib != null) + final String libraryName = System.getProperty("org.usb4java.LibraryName"); + if (libraryName != null) { - System.load(extractLibrary(platform, extraLib)); + System.loadLibrary(libraryName); + } + else + { + final String platform = getPlatform(); + final String lib = getLibName(); + final String extraLib = getExtraLibName(); + if (extraLib != null) + { + System.load(extractLibrary(platform, extraLib)); + } + System.load(extractLibrary(platform, lib)); } - System.load(extractLibrary(platform, lib)); } }