Skip to content

Commit

Permalink
Version 0.0.6 - major overhaul of the code base -- works in progress
Browse files Browse the repository at this point in the history
  • Loading branch information
nyholku committed Sep 11, 2016
1 parent 54598fa commit 1616cbd
Show file tree
Hide file tree
Showing 16 changed files with 331 additions and 112 deletions.
10 changes: 6 additions & 4 deletions src/purejavahidapi/HidDeviceInfo.java
Original file line number Diff line number Diff line change
Expand Up @@ -52,14 +52,15 @@ public class HidDeviceInfo {
protected String m_ManufactureString;
protected String m_ProductString;

/**
/**
* This method returns a string that represents a platform dependent path
* that describes the 'physical' path through hubs and ports to the device.
* <p>
* The main use of the path is to pass it to the
* {@link PureJavaHidApi#openDevice(String) to obtain an instance {
* {@link PureJavaHidApi#openDevice(String) to obtain an instance
*
* @link HidDevice} which can subsequently be used to communicate with the
* device.
* device.
*
* @return a string representing a 'path' to the device
*/
Expand Down Expand Up @@ -155,8 +156,9 @@ public String getProductString() {
public String getSerialNumberString() {
return m_SerialNumberString;
}

public String getDeviceId() {
return m_DeviceId;
}

}
40 changes: 22 additions & 18 deletions src/purejavahidapi/PureJavaHidApi.java
Original file line number Diff line number Diff line change
Expand Up @@ -34,18 +34,19 @@
import java.util.List;

import purejavahidapi.shared.Backend;
import purejavahidapi.shared.Frontend;

import com.sun.jna.Platform;

/** PureJavaHidApi class is the entry point to access USB HID devices.
/**
* PureJavaHidApi class is the entry point to access USB HID devices.
* <p>
* Static methods in PureJavaHidApi allow enumeration and opening of HID devices.
* Static methods in PureJavaHidApi allow enumeration and opening of HID
* devices.
* <p>
* {@link #enumerateDevices(int, int)} method returns a iist of HidDeviceInfo
* objects from which a device path can be obtained. The path can be passed to
* the {@link #openDevice(String)} method to obtain a {@link HidDevice} object which
* can then be used to communicate with the device.
* {@link #enumerateDevices(int, int)} method returns a iist of HidDeviceInfo
* objects from which a device path can be obtained. The path can be passed to
* the {@link #openDevice(String)} method to obtain a {@link HidDevice} object
* which can then be used to communicate with the device.
* <p>
* See javadoc for above mentioned classes and methods for details.
*
Expand All @@ -61,21 +62,21 @@ public class PureJavaHidApi {
* @return PureJavaHidApi library version string
*/
public String getVersion() {
return "0.0.5";
return "0.0.6";
}

/**
* Returns a list of available USB HID devices.
* <p>
* Passing a 0 for the vendorId or productId macthes everything and thus works
* as a wild card for matching. Passing 0 for both will return a list
* Passing a 0 for the vendorId or productId macthes everything and thus
* works as a wild card for matching. Passing 0 for both will return a list
* of all USB HID devices.
*
* @return List of HidDeviceInfo objects representing the matching devices.
*/
public static List<HidDeviceInfo> enumerateDevices() {
synchronized (m_Mutex) {
if (m_Backend==null)
if (m_Backend == null)
throw new IllegalStateException("Unsupported platform");
return m_Backend.enumerateDevices();
}
Expand All @@ -84,23 +85,26 @@ public static List<HidDeviceInfo> enumerateDevices() {
/**
* Given a device path opens a USB device for communication.
*
* @param path A path obtained from a HidDeviceInfo object.
* @return An instance of HidDevice that can be used to communicate with the HID device.
* @throws IOException if the device cannot be opened
* @param path
* A path obtained from a HidDeviceInfo object.
* @return An instance of HidDevice that can be used to communicate with the
* HID device.
* @throws IOException
* if the device cannot be opened
* @see HidDeviceInfo#getPath()
*/
public static HidDevice openDevice(HidDeviceInfo path) throws IOException {
synchronized (m_Mutex) {
if (m_Backend==null)
if (m_Backend == null)
throw new IllegalStateException("Unsupported platform");
HidDevice device = m_Backend.openDevice(path);
if (device!=null)
if (device != null)
m_OpenDevices.add(device);
return device;
}
}

static {
static {
if (Platform.isMac()) {
m_Backend = new purejavahidapi.macosx.MacOsXBackend();
} else if (Platform.isWindows()) {
Expand All @@ -109,7 +113,7 @@ public static HidDevice openDevice(HidDeviceInfo path) throws IOException {
m_Backend = new purejavahidapi.linux.LinuxBackend();
} else
m_Backend = null;
if (m_Backend!=null)
if (m_Backend != null)
m_Backend.init();
}
}
102 changes: 102 additions & 0 deletions src/purejavahidapi/linux/CLibrary.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
package purejavahidapi.linux;

import java.util.Arrays;
import java.util.List;

import purejavahidapi.linux.UdevLibrary.hidraw_report_descriptor;

import com.sun.jna.Library;
import com.sun.jna.Native;
import com.sun.jna.NativeLong;
import com.sun.jna.Structure;

public class CLibrary {
static CLibraryInterface INSTANCE = (CLibraryInterface) Native.loadLibrary("c", CLibraryInterface.class);

public static short POLLIN = 0x0001;

interface CLibraryInterface extends Library {
int open(String pathname, int flags);

int close(int fd);

int read(int fd, byte[] data, NativeLong len);

int write(int fd, byte[] data, NativeLong len);

int ioctl(int fd, int cmd, int[] p);

int ioctl(int fd, int cmd, byte[] p);

int ioctl(int fd, int cmd, hidraw_report_descriptor p);

int poll(pollfd[] fds, int nfds, int timeout);

public int pipe(int[] fds);
}

static public class pollfd extends Structure {

public static class ByReference extends pollfd implements Structure.ByReference {
}

public int fd;
public short events;
public short revents;

@Override
protected List getFieldOrder() {
return Arrays.asList(//
"fd",//
"events",//
"revents"//
);
}

public pollfd() {
}

public pollfd(int fd, short events, short revents) {
this.fd = fd;
this.events = events;
this.revents = revents;
}
}

public static int open(String pathname, int flags) {
return INSTANCE.open(pathname, flags);
}

public static void close(int fd) {
INSTANCE.close(fd);
}

public static int ioctl(int fd, int cmd, int[] p) {
return INSTANCE.ioctl(fd, cmd, p);
}

public static int ioctl(int fd, int cmd, byte[] p) {
return INSTANCE.ioctl(fd, cmd, p);
}

public static int ioctl(int fd, int cmd, hidraw_report_descriptor p) {
return INSTANCE.ioctl(fd, cmd, p);
}

public static int read(int fd, byte[] buffer, int len) {
return INSTANCE.read(fd, buffer, new NativeLong(len));
}

public static int write(int fd, byte[] buffer, int len) {
return INSTANCE.write(fd, buffer, new NativeLong(len));
}

public static int poll(pollfd fds[], int nfds, int timeout) {
return INSTANCE.poll(fds, nfds, timeout);
}

public static int pipe(int[] fds) {
return INSTANCE.pipe(fds);
}

}
71 changes: 71 additions & 0 deletions src/purejavahidapi/linux/HIDRAW.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
/*
* Copyright (c) 2016, Kustaa Nyholm / SpareTimeLabs
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* Redistributions of source code must retain the above copyright notice, this list
* of conditions and the following disclaimer.
*
* Redistributions in binary form must reproduce the above copyright notice, this
* list of conditions and the following disclaimer in the documentation and/or other
* materials provided with the distribution.
*
* Neither the name of the Kustaa Nyholm or SpareTimeLabs nor the names of its
* contributors may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
* IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
* INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
* OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
* OF SUCH DAMAGE.
*/
package purejavahidapi.linux;

import static purejavahidapi.linux.IOCtl.*;

public class HIDRAW {
public static int HIDIOCSFEATURE(int len) {
return _IOC(_IOC_WRITE|_IOC_READ, 'H', 0x06, len);
}
public static int HIDIOCGFEATURE(int len) {
return _IOC(_IOC_WRITE|_IOC_READ, 'H', 0x07, len);
}



/*
struct hidraw_report_descriptor {
22 __u32 size;
23 __u8 value[HID_MAX_DESCRIPTOR_SIZE];
24 };
25
26 struct hidraw_devinfo {
27 __u32 bustype;
28 __s16 vendor;
29 __s16 product;
30 };
31
32 /* ioctl interface
33 #define HIDIOCGRDESCSIZE _IOR('H', 0x01, int)
34 #define HIDIOCGRDESC _IOR('H', 0x02, struct hidraw_report_descriptor)
35 #define HIDIOCGRAWINFO _IOR('H', 0x03, struct hidraw_devinfo)
36 #define HIDIOCGRAWNAME(len) _IOC(_IOC_READ, 'H', 0x04, len)
37 #define HIDIOCGRAWPHYS(len) _IOC(_IOC_READ, 'H', 0x05, len)
38 /* The first byte of SFEATURE and GFEATURE is the report number
39 #define HIDIOCSFEATURE(len) _IOC(_IOC_WRITE|_IOC_READ, 'H', 0x06, len)
40 #define HIDIOCGFEATURE(len) _IOC(_IOC_WRITE|_IOC_READ, 'H', 0x07, len)
41
42 #define HIDRAW_FIRST_MINOR 0
43 #define HIDRAW_MAX_DEVICES 64
44 /* number of reports to buffer
45 #define HIDRAW_BUFFER_SIZE 64
*/
}
19 changes: 7 additions & 12 deletions src/purejavahidapi/linux/HidDevice.java
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,6 @@

import purejavahidapi.*;
import purejavahidapi.linux.UdevLibrary.*;
import purejavahidapi.shared.Frontend;
import purejavahidapi.shared.SyncPoint;
import static purejavahidapi.linux.UdevLibrary.*;
import static purejavahidapi.linux.CLibrary.*;
Expand All @@ -57,16 +56,12 @@ public class HidDevice extends purejavahidapi.HidDevice {
private byte[] m_OutputReportBytes;

/* package */HidDevice(purejavahidapi.HidDeviceInfo deviceInfo, LinuxBackend backend) throws IOException {
m_Backend=backend;
m_HidDeviceInfo=deviceInfo;
udev_device raw_dev = udev_device_new_from_syspath(backend.m_udev, m_HidDeviceInfo.getPath());
m_Backend = backend;
m_HidDeviceInfo = deviceInfo;
udev udev=udev_new();
udev_device raw_dev = udev_device_new_from_syspath(udev, m_HidDeviceInfo.getPath());
String dev_path = udev_device_get_devnode(raw_dev);
System.out.println("hid dev path " + dev_path);

udev_device usbdev = udev_device_get_parent_with_subsystem_devtype(raw_dev, "usb", "usb_device");
String usb_dev_path = udev_device_get_devnode(usbdev);
System.out.println("usb dev path " + usb_dev_path);

udev_unref(udev);

m_DeviceHandle = open(dev_path, O_RDWR);

Expand Down Expand Up @@ -105,8 +100,6 @@ public class HidDevice extends purejavahidapi.HidDevice {
m_SyncStart = new SyncPoint(2);
m_SyncShutdown = new SyncPoint(2);

backend.addDevice(usb_dev_path, this);

m_Thread = new Thread(new Runnable() {
@Override
public void run() {
Expand All @@ -117,6 +110,7 @@ public void run() {
}
}
}, m_HidDeviceInfo.getPath());
m_Backend.addDevice(m_HidDeviceInfo.getDeviceId(), this);
m_Open = true;
m_Thread.start();
m_SyncStart.waitAndSync();
Expand Down Expand Up @@ -171,6 +165,7 @@ public void close() {
CLibrary.close(m_NudgePipeWriteHandle);
CLibrary.close(m_NudgePipeReadHandle);
m_Backend.removeDevice(m_HidDeviceInfo.getDeviceId());

m_Open = false;
}

Expand Down
Loading

0 comments on commit 1616cbd

Please sign in to comment.