summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--hidapi-sys/.gitignore2
-rw-r--r--hidapi-sys/Cargo.toml24
-rw-r--r--hidapi-sys/build.rs81
-rw-r--r--hidapi-sys/src/lib.rs68
4 files changed, 175 insertions, 0 deletions
diff --git a/hidapi-sys/.gitignore b/hidapi-sys/.gitignore
new file mode 100644
index 0000000..a9d37c5
--- /dev/null
+++ b/hidapi-sys/.gitignore
@@ -0,0 +1,2 @@
+target
+Cargo.lock
diff --git a/hidapi-sys/Cargo.toml b/hidapi-sys/Cargo.toml
new file mode 100644
index 0000000..15b4e9e
--- /dev/null
+++ b/hidapi-sys/Cargo.toml
@@ -0,0 +1,24 @@
+[package]
+name = "hidapi-sys"
+version = "0.1.2"
+build = "build.rs"
+links = "hidapi"
+
+authors = ["meh. <meh@schizofreni.co>"]
+license = "WTFPL"
+
+description = "FFI bindings to hidapi"
+repository = "https://github.com/meh/rust-hidapi-sys"
+keywords = ["hid"]
+categories = ["external-ffi-bindings", "hardware-support", "os"]
+
+[features]
+static = []
+build = ["static"]
+
+[dependencies]
+libc = "0.2"
+
+[build-dependencies]
+gcc = "0.3"
+pkg-config = "0.3"
diff --git a/hidapi-sys/build.rs b/hidapi-sys/build.rs
new file mode 100644
index 0000000..6ad9197
--- /dev/null
+++ b/hidapi-sys/build.rs
@@ -0,0 +1,81 @@
+extern crate gcc;
+extern crate pkg_config;
+
+use std::env;
+use std::io;
+use std::path::PathBuf;
+use std::process::Command;
+
+fn main() {
+ if env::var("CARGO_FEATURE_BUILD").is_err() {
+ return;
+ }
+
+ fetch().unwrap();
+ build().unwrap();
+
+ println!("cargo:rustc-link-search=native={}", output().to_string_lossy());
+}
+
+fn output() -> PathBuf {
+ PathBuf::from(env::var("OUT_DIR").unwrap())
+}
+
+fn source() -> PathBuf {
+ output().join("hidapi")
+}
+
+fn fetch() -> io::Result<()> {
+ Command::new("git")
+ .current_dir(&output())
+ .arg("clone")
+ .arg("https://github.com/signal11/hidapi.git")
+ .arg("hidapi")
+ .status()?;
+
+ Ok(())
+}
+
+#[cfg(target_os = "linux")]
+fn build() -> io::Result<()> {
+ let mut config = gcc::Config::new();
+
+ config.file(source().join("libusb/hid.c"));
+ config.include(source().join("hidapi"));
+
+ for path in pkg_config::find_library("libusb-1.0").unwrap().include_paths {
+ config.include(path.to_str().unwrap());
+ }
+
+ config.compile("libhidapi-libusb.a");
+
+ Ok(())
+}
+
+#[cfg(target_os = "macos")]
+fn build() -> io::Result<()> {
+ let mut config = gcc::Config::new();
+
+ config.file(source().join("libusb/hid.c"));
+ config.include(source().join("hidapi"));
+
+ for path in pkg_config::find_library("libusb-1.0").unwrap().include_paths {
+ config.include(path.to_str().unwrap());
+ }
+
+ config.compile("libhidapi.a");
+
+ Ok(())
+}
+
+#[cfg(target_os = "windows")]
+fn build() -> io::Result<()> {
+ let mut config = gcc::Config::new();
+
+ config.file(source().join("windows/hid.c"));
+ config.include(source().join("hidapi"));
+
+ config.compile("libhidapi.a");
+
+ Ok(())
+}
diff --git a/hidapi-sys/src/lib.rs b/hidapi-sys/src/lib.rs
new file mode 100644
index 0000000..656bd47
--- /dev/null
+++ b/hidapi-sys/src/lib.rs
@@ -0,0 +1,68 @@
+#![allow(non_camel_case_types, non_snake_case, non_upper_case_globals)]
+
+extern crate libc;
+
+use libc::{c_void, c_ushort, wchar_t, c_int, c_uchar, size_t, c_char};
+
+pub type hid_device = c_void;
+
+#[repr(C)]
+pub struct hid_device_info {
+ pub path: *mut c_char,
+
+ pub vendor_id: c_ushort,
+ pub product_id: c_ushort,
+
+ pub serial_number: *mut wchar_t,
+ pub release_number: c_ushort,
+
+ pub manufacturer_string: *mut wchar_t,
+ pub product_string: *mut wchar_t,
+
+ pub usage_page: c_ushort,
+ pub usage: c_ushort,
+
+ pub interface_number: c_int,
+
+ pub next: *mut hid_device_info,
+}
+
+#[cfg_attr(target_os = "linux", link(name = "udev"))]
+extern "C" { }
+
+#[cfg_attr(target_os = "windows", link(name = "setupapi"))]
+extern "C" { }
+
+#[cfg_attr(all(feature = "static", target_os = "linux"), link(name = "hidapi-libusb", kind = "static"))]
+#[cfg_attr(all(not(feature = "static"), target_os = "linux"), link(name = "hidapi-libusb"))]
+#[cfg_attr(all(feature = "static", not(target_os = "linux")), link(name = "hidapi", kind = "static"))]
+#[cfg_attr(all(not(feature = "static"), not(target_os = "linux")), link(name = "hidapi"))]
+extern "C" {
+ pub fn hid_init() -> c_int;
+ pub fn hid_exit() -> c_int;
+
+ pub fn hid_enumerate(vendor_id: c_ushort, product_id: c_ushort) -> *mut hid_device_info;
+ pub fn hid_free_enumeration(devs: *mut hid_device_info);
+
+ pub fn hid_open(vendor_id: c_ushort, product_id: c_ushort, serial_number: *const wchar_t) -> *mut hid_device;
+ pub fn hid_open_path(path: *const c_char) -> *mut hid_device;
+
+ pub fn hid_write(device: *mut hid_device, data: *const c_uchar, length: size_t) -> c_int;
+
+ pub fn hid_read_timeout(device: *mut hid_device, data: *mut c_uchar, length: size_t, milleseconds: c_int) -> c_int;
+ pub fn hid_read(device: *mut hid_device, data: *mut c_uchar, length: size_t) -> c_int;
+
+ pub fn hid_set_nonblocking(device: *mut hid_device, nonblock: c_int) -> c_int;
+
+ pub fn hid_send_feature_report(device: *mut hid_device, data: *const c_uchar, length: size_t) -> c_int;
+ pub fn hid_get_feature_report(device: *mut hid_device, data: *mut c_uchar, length: size_t) -> c_int;
+
+ pub fn hid_close(device: *mut hid_device);
+
+ pub fn hid_get_manufacturer_string(device: *mut hid_device, string: *mut wchar_t, maxlen: size_t) -> c_int;
+ pub fn hid_get_product_string(device: *mut hid_device, string: *mut wchar_t, maxlen: size_t) -> c_int;
+ pub fn hid_get_serial_number_string(device: *mut hid_device, string: *mut wchar_t, maxlen: size_t) -> c_int;
+ pub fn hid_get_indexed_string(device: *mut hid_device, string_index: c_int, string: *mut wchar_t, maxlen: size_t) -> c_int;
+
+ pub fn hid_error(device: *mut hid_device) -> *const wchar_t;
+}