{"id":20520834,"url":"https://github.com/manuelbl/javadoesusb","last_synced_at":"2025-04-05T05:07:14.672Z","repository":{"id":57752461,"uuid":"527161408","full_name":"manuelbl/JavaDoesUSB","owner":"manuelbl","description":"USB library for Java","archived":false,"fork":false,"pushed_at":"2025-02-23T20:13:11.000Z","size":2587,"stargazers_count":153,"open_issues_count":10,"forks_count":11,"subscribers_count":5,"default_branch":"main","last_synced_at":"2025-03-29T04:08:45.077Z","etag":null,"topics":["java","java-library","java-native","java-panama","jdk19","usb"],"latest_commit_sha":null,"homepage":"","language":"C","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/manuelbl.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2022-08-21T09:34:49.000Z","updated_at":"2025-02-28T12:47:35.000Z","dependencies_parsed_at":"2024-04-19T13:46:42.732Z","dependency_job_id":"43669761-7268-4f8d-96cb-246bda3ea151","html_url":"https://github.com/manuelbl/JavaDoesUSB","commit_stats":null,"previous_names":[],"tags_count":15,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/manuelbl%2FJavaDoesUSB","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/manuelbl%2FJavaDoesUSB/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/manuelbl%2FJavaDoesUSB/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/manuelbl%2FJavaDoesUSB/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/manuelbl","download_url":"https://codeload.github.com/manuelbl/JavaDoesUSB/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247289428,"owners_count":20914464,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["java","java-library","java-native","java-panama","jdk19","usb"],"created_at":"2024-11-15T22:23:36.132Z","updated_at":"2025-04-05T05:07:14.645Z","avatar_url":"https://github.com/manuelbl.png","language":"C","readme":"# Java Does USB: USB Library for Java\n\n[![javadoc](https://javadoc.io/badge2/net.codecrete.usb/java-does-usb/javadoc.svg)](https://javadoc.io/doc/net.codecrete.usb/java-does-usb)\n\n*Java Does USB* is a Java library for working with USB devices. It allows to query the conntected USB devices and to communicate with them using custom / vendor specific protocols. It is not intended for communication with standard types of USB devices such as mass storage devices, keyboards etc.\n\nThe library uses the [Foreign Function and Memory API](https://docs.oracle.com/en/java/javase/22/core/foreign-function-and-memory-api.html) to access native APIs of the underlying operating system. It is written entirely in Java and does not use JNI or any native third-party library. The *Foreign Function and Memory API* has been introduced with Java 22.\n\n\n\n## Features\n\n- Single API for all operating systems (similar to WebUSB API)\n- Enumeration of USB devices\n- Control, bulk and interrupt transfers (optionally with timeout)\n- Notifications about connected/disconnected devices\n- Descriptive information about interfaces, settings and endpoints\n- High-throughput input/output streams\n- Support for alternate interface settings, composite devices and interface association\n- Published on Maven Central and licensed under the permissive MIT license\n\n\n\n## Getting Started\n\nThe library is available at Maven Central. To use it, just add it to your Maven or Gradle project.\n\nIf you are using Maven, add the below dependency to your pom.xml:\n\n```xml\n\u003cdependency\u003e\n      \u003cgroupId\u003enet.codecrete.usb\u003c/groupId\u003e\n      \u003cartifactId\u003ejava-does-usb\u003c/artifactId\u003e\n      \u003cversion\u003e1.2.0\u003c/version\u003e\n\u003c/dependency\u003e\n```\n\nIf you are using Gradle, add the below dependency to your build.gradle file:\n\n```groovy\ncompile group: 'net.codecrete.usb', name: 'java-does-usb', version: '1.2.0'\n```\n\n```java\npackage net.codecrete.usb.sample;\n\nimport net.codecrete.usb.Usb;\n\npublic class EnumerateDevices {\n\n    public static void main(String[] args) {\n        for (var device : Usb.getDevices()) {\n            System.out.println(device);\n        }\n    }\n}\n```\n\n\n\n## Documentation\n\n- [Code Examples](https://github.com/manuelbl/JavaDoesUSB/wiki/Java-Does-USB-By-Examples)\n- [Javadoc](https://javadoc.io/doc/net.codecrete.usb/java-does-usb)\n\n\n\n## Examples\n\n- [Bulk Transfer](examples/bulk_transfer/) demonstrates how to find a USB device, open it and communicate using bulk transfer.\n- Enumeration ([Java](examples/enumerate/) / [Kotlin](examples/enumerate_kotlin/)) lists all connected USB devices and displays information about interfaces and endpoints.\n- Monitor ([Java](examples/monitor/) / [Kotlin](examples/monitor_kotlin/)) lists the connected USB devices and then monitors for devices being connected and disconnected.\n- [Device Firmware Upload (DFU) for STM32](examples/stm_dfu) uploads firmware to STM32 microcontrollers supporting the built-in DFU mode.\n- [ePaper Display](examples/epaper_display) communicates with an IT8951 controller for e-Paper displays and shows an image on the display.\n\n\n\n## Prerequisite\n\n- Java 22 or higher, available at [jdk.java.net](https://jdk.java.net/), [Azul](https://www.azul.com/downloads/?package=jdk), [Adoptium](https://adoptium.net/temurin/releases/) or with your favorite package manager.\n- Windows (x86 64-bit, ARM 64-bit), macOS (x86 64-bit, ARM 64-bit) or Linux 64 bit (x86 64-bit, ARM 64-bit).\n\n\n\n## Platform-specific Considerations\n\n\n### macOS\n\nNo special considerations apply. Using this library, a Java application can connect to any USB device and claim any interface that isn't claimed by an operating system driver or another application. Standard operation system drivers can be unloaded if the application is run with *root* privileges. It runs both on Macs with Apple Silicon and Intel processors.\n\n\n### Linux\n\n*libudev* is used to discover and monitor USB devices. It is closely tied to *systemd*. So the library runs on Linux distributions with *systemd* and the related libraries. The majority of Linux distributions suitable for desktop computing (as opposed to distributions optimized for containers) fulfill this requirement. It runs on both Intel/AMD and ARM processors.\n\nSimilar to macOS, a Java application can connect to any USB device and claim any interface that isn't claimed by an operating system driver or another application. Standard operation system drivers can be unloaded (without the need for root privileges).\n\nMost Linux distributions set up user accounts without permissions to access USB devices. The *udev* system daemon is responsible for assigning permissions to USB devices. It can be configured to assign specific permissions or ownership:\n\nCreate a file called `/etc/udev/rules.d/80-javadoesusb-udev.rules` with the below content:\n\n```text\nSUBSYSTEM==\"usb\", ATTRS{idVendor}==\"cafe\", MODE=\"0666\"\n```\n\nThis adds the rule to assign permission mode 0666 to all USB devices with vendor ID `0xCAFE`. This unregistered vendor ID is used by the test devices.\n\nWithout the *udev* rule, it is still possible to enumerate and query all USB devices.\n\n\n### Windows\n\nThe Windows driver model is rather rigid. It's not possible to open a USB device unless it uses the *WinUSB* driver. This even applies to devices with no installed driver. Enumerating and querying USB devices is possible independent of the driver.\n\nUSB devices can implement special control requests to instruct Windows to automatically install the WinUSB driver (search for *WCID* or *Microsoft OS Compatibility Descriptors*). The WinUSB driver can also be manually installed or replaced using a software called [Zadig](https://zadig.akeo.ie/).\n\nThe test devices implement the required control requests. So the driver is installed automatically.\n\nThe implementation runs on both Windows for Intel/AMD and ARM processors. Few OpenJDK distributions support Windows on ARM, and they do not support all recent versions of Java. [Eclipse Temurin](https://adoptium.net/temurin/releases/?os=windows\u0026arch=aarch64\u0026version=23) has released a version for Java 23.\n\n\n\n## Troubleshooting\n\n### 32-bit versions\n\nThe *Foreign Function And Memory API* has not been implemented for 32-bit operating systems / JDKs (and likely never will be).\n\n\n\n## Running on older JDK versions\n\nThe *Foreign Function And Memory API* has been available as a preview feature in JDKs before 22. However, incompatible changes were made from preview to preview to release. Earlier versions can be used with specific versions of this library:\n\n| Version | Main New Features | Compatibility |\n| - | - | - |\n| 1.x.x | Release for final Java API | JDK 22 and higher |\n| 0.7.x | New setter/getter names for improved Kotlin support; Kotlin examples | JDK 21 |\n| 0.6.x | Support for JDK 21; better handling of composite devices on Windows | JDK 21 |\n| 0.5.x | Support for JDK 20; high-throuput I/O streams | JDK 20 |\n| 0.4.x | Early release | JDK 19 |\n\nWhen using an older JDK, preview features must be enabled using the `--enable-preview` VM option.\n\n\n\n## Building from source\n\nTo build from source, run the following command:\n\n```\ncd java-does-usb\nmvn clean install -DskipTests\n```\n\nThe tests are skipped as they require that a special test device is connected to the computer. See the next section for more information.\n\n\n\n## Testing\n\nIn order to run the unit tests, a special test device must be connected to the computer, which can be easily created from very inexpensive microcontroller boards. Two variants exist:\n\n- [loopback-stm32](test-devices/loopback-stm32)\n- [composite-stm32](test-devices/composite-stm32)\n\nThe test device with the *loopback-stm32* code supports all tests. If the test device with the *composite-stm32* code is connected, some tests are skipped. However, if it is used, the correct handling of composite devices is verified.\n\nTests can be run from the command line:\n\n```\ncd java-does-usb\nmvn clean test\n```\n\nIf they are run from an IDE (such as IntelliJ IDEA), you must likely configure VM options to allow native access:\n\n```\n--enable-native-access=net.codecrete.usb\n```\n\nOr (if modules are ignored):\n\n```\n--enable-native-access=ALL-UNNAMED\n```\n\n\n\n## Code generation\n\nMany bindings for the native APIs have been generated with *jextract*. See the [jextract](java-does-usb/jextract) subdirectory for more information. For functions that need to retain the error state (`errno` on Linux, `GetLastError()` on Windows), the bindings have been manually written as *jextract* does not support it.\n\nSince the code can only be generated for the current operating system, it must be generated on separate computers for Linux, Windows and macOS. Thus, the generated code is included in the repository. The generated code is compilable on all operating systems.\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmanuelbl%2Fjavadoesusb","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmanuelbl%2Fjavadoesusb","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmanuelbl%2Fjavadoesusb/lists"}