mirror of
https://github.com/joleuger/vuinputd.git
synced 2026-07-17 16:36:03 +00:00
Updated documentation for release readiness
This commit is contained in:
parent
6afa8acaa8
commit
effc17647b
5 changed files with 98 additions and 0 deletions
|
|
@ -12,6 +12,8 @@ This crate is heavily based on libfuse-sys by Richard Wiedenhöft. See the [orig
|
||||||
|
|
||||||
This fork here contains only the relevant subset of code of libfuse-sys to access the low-level api of cuse.
|
This fork here contains only the relevant subset of code of libfuse-sys to access the low-level api of cuse.
|
||||||
|
|
||||||
|
This crate does not attempt to abstract or validate cuse usage; it only provides wrappers. Higher-level logic (such as event management or device configuration) should be built on top.
|
||||||
|
|
||||||
## Using cuse-lowlevel
|
## Using cuse-lowlevel
|
||||||
|
|
||||||
Add the dependencies to your Cargo.toml
|
Add the dependencies to your Cargo.toml
|
||||||
|
|
|
||||||
|
|
@ -110,3 +110,28 @@ While this design is necessary for mediation, it introduces potential attack sur
|
||||||
* [ ] Enforce **container identity** using cgroup, namespace, or pidfd checks.
|
* [ ] Enforce **container identity** using cgroup, namespace, or pidfd checks.
|
||||||
* [ ] Use **seccomp** or `systemd` sandboxing (`ProtectSystem`, `ProtectKernelTunables`, `RestrictNamespaces`, etc.).
|
* [ ] Use **seccomp** or `systemd` sandboxing (`ProtectSystem`, `ProtectKernelTunables`, `RestrictNamespaces`, etc.).
|
||||||
* [ ] Eventually migrate to **Rust-native FUSE/Netlink** bindings to remove unsafe dependencies.
|
* [ ] Eventually migrate to **Rust-native FUSE/Netlink** bindings to remove unsafe dependencies.
|
||||||
|
|
||||||
|
## 5. Alternative Approaches
|
||||||
|
|
||||||
|
### 5.1 trace accesses of /dev/uinput with eBPF
|
||||||
|
|
||||||
|
**Idea (short):** attach an eBPF program to the syscall tracepoint for `ioctl` (`tracepoint/syscalls/sys_enter_ioctl`), filter by container cgroup, and send small events (pid, tgid, fd, cmd, timestamp, short payload sample) to userspace using the BPF ring buffer. A privileged host agent consumes the ringbuf events, duplicates the target FD via `pidfd_getfd()` and proceeds with UI_GET_SYSNAME / sysfs resolution to retrieve the sys-path and the dev-path. Having the dev-path and the pid of the container, the solution could proceed as in the current solution.
|
||||||
|
|
||||||
|
#### 1) Trace hook: `tracepoint/syscalls/sys_enter_ioctl`
|
||||||
|
|
||||||
|
Use the *syscall tracepoint* `syscalls:sys_enter_ioctl`. Tracepoints are stable, exported kernel probe points and the syscall tracepoint provides the syscall arguments (fd, cmd, arg) in a stable layout. This avoids fragile kprobe offsets on architecture-specific syscall wrappers. See the kernel tracepoint docs.
|
||||||
|
|
||||||
|
#### 2) BPF map: ring buffer (kernel → userspace)
|
||||||
|
|
||||||
|
Use the BPF ring buffer (`BPF_MAP_TYPE_RINGBUF`) to cheaply publish fixed-size events to userspace. The ring buffer provides `bpf_ringbuf_reserve()` / `bpf_ringbuf_submit()` semantics from the kernel side and is the recommended modern replacement for perf-buf for high-rate kernel→user events. See the kernel documentation for the ring buffer API.
|
||||||
|
|
||||||
|
#### 3) Useful eBPF helpers
|
||||||
|
|
||||||
|
Inside the trace program you will typically use:
|
||||||
|
|
||||||
|
* `bpf_get_current_pid_tgid()` to record tgid/pid,
|
||||||
|
* `bpf_get_current_cgroup_id()` to filter to the container cgroup you care about,
|
||||||
|
* `bpf_copy_from_user()` to safely copy up to `N` bytes from the user pointer (`arg`) into the event buffer.
|
||||||
|
|
||||||
|
#### 4) Use of `pidfd_getfd`
|
||||||
|
The **`pidfd_getfd()`** syscall (introduced in Linux 5.6, see `man pidfd_getfd(2)`) allows one process to **duplicate a file descriptor from another process** into its own FD table. It takes a *pidfd* (obtained via `pidfd_open()` or from `CLONE_PIDFD`), the target FD number in the remote process, and optional flags. The resulting descriptor refers to the **same open file description**—sharing offset, status flags, and driver state—exactly as if the target process had called `dup()`. Permission checks apply: the caller must either share credentials (same UID) or hold `CAP_SYS_PTRACE` or an equivalent capability over the target. This makes `pidfd_getfd()` the canonical and race-free way to inspect or reuse another process’s device handles (for example, to run `UI_GET_SYSNAME` on a client apps' fd on `/dev/uinput` ) without invasive ptrace tricks.
|
||||||
|
|
|
||||||
14
docs/USAGE.md
Normal file
14
docs/USAGE.md
Normal file
|
|
@ -0,0 +1,14 @@
|
||||||
|
# Host
|
||||||
|
|
||||||
|
## systemd-nspawn
|
||||||
|
```
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
|
## docker
|
||||||
|
|
||||||
|
## lxd/lxc
|
||||||
|
|
||||||
|
|
||||||
|
# Container
|
||||||
|
|
||||||
|
|
@ -2,6 +2,13 @@
|
||||||
name = "uinput-ioctls"
|
name = "uinput-ioctls"
|
||||||
version = "0.1.0"
|
version = "0.1.0"
|
||||||
edition = "2021"
|
edition = "2021"
|
||||||
|
license = "MIT"
|
||||||
|
description = "Rust bindings for Linux uinput ioctl constants and helper macros."
|
||||||
|
repository = "https://github.com/joleuger/vuinputd"
|
||||||
|
authors = ["Johannes Leupolz <dev@leupolz.eu>"]
|
||||||
|
categories = ["external-ffi-bindings"]
|
||||||
|
keywords = ["uinput", "ioctl"]
|
||||||
|
readme = "README.md"
|
||||||
|
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
|
|
|
||||||
50
uinput-ioctls/README.md
Normal file
50
uinput-ioctls/README.md
Normal file
|
|
@ -0,0 +1,50 @@
|
||||||
|
# uinput-ioctls
|
||||||
|
|
||||||
|
**uinput-ioctls** provides Rust bindings and constants for the Linux [`uinput`](https://www.kernel.org/doc/html/latest/input/uinput.html) subsystem's ioctl interface.
|
||||||
|
|
||||||
|
It exposes `ioctl_*` helper functions and constants based on the Linux kernel's `uinput.h`, allowing you to interact with virtual input devices (keyboards, mice, gamepads, etc.) through Rust in a low-level but type-safe way.
|
||||||
|
|
||||||
|
This crate does not attempt to abstract or validate ioctl usage; it only provides constants and wrappers. Higher-level logic (such as event management or device configuration) should be built on top.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## ✨ Features
|
||||||
|
|
||||||
|
- Idiomatic Rust wrappers around `uinput` ioctl definitions.
|
||||||
|
- Uses the [`nix`](https://crates.io/crates/nix) crate for safe `ioctl` macros.
|
||||||
|
- Includes all `UI_*` constants and corresponding helper functions:
|
||||||
|
- `ui_dev_create`, `ui_dev_destroy`
|
||||||
|
- `ui_dev_setup`, `ui_abs_setup`
|
||||||
|
- `ui_set_evbit`, `ui_set_keybit`, ...
|
||||||
|
- `ui_begin_ff_upload`, `ui_end_ff_upload`, etc.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 🧰 Example
|
||||||
|
|
||||||
|
[Mouse example](https://github.com/joleuger/vuinputd/blob/main/vuinput-examples/src/bin/mouse-advanced.rs)
|
||||||
|
|
||||||
|
|
||||||
|
[Keyboard example](https://github.com/joleuger/vuinputd/blob/main/vuinput-examples/src/bin/keyboard-advanced.rs)
|
||||||
|
|
||||||
|
> ⚠️ Requires Linux and appropriate permissions to access `/dev/uinput`.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 🧩 Related Crates
|
||||||
|
|
||||||
|
* [`uinput`](https://crates.io/crates/uinput): High-level abstraction for creating virtual input devices.
|
||||||
|
* [`nix`](https://crates.io/crates/nix): Provides low-level Unix system call wrappers and `ioctl` macros.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 📜 License
|
||||||
|
|
||||||
|
Licensed under the [MIT License](LICENSE).
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 👤 Author
|
||||||
|
|
||||||
|
**Johannes Leupolz**
|
||||||
|
[dev@leupolz.eu](mailto:dev@leupolz.eu)
|
||||||
Loading…
Add table
Add a link
Reference in a new issue