Struct UninitDevice

Source
pub struct UninitDevice { /* private fields */ }
Expand description

Opaque struct representing an evdev device with no backing file

Implementations§

Source§

impl UninitDevice

Source

pub fn new() -> Option<UninitDevice>

Initialize a new libevdev device.

Generally you should use Device::new_from_file instead of this method This function only initializes the struct to sane default values. To actually hook up the device to a kernel device, use set_file.

Examples found in repository?
examples/evtest.rs (line 125)
104fn main() {
105    let mut args = std::env::args();
106
107    if args.len() != 2 {
108        usage();
109        std::process::exit(1);
110    }
111
112    let path = &args.nth(1).unwrap();
113    let mut file = OpenOptions::new()
114        .read(true)
115        .write(true)
116        .custom_flags(libc::O_NONBLOCK)
117        .open(path)
118        .unwrap();
119    let mut buffer = Vec::new();
120    let result = file.read_to_end(&mut buffer);
121    if result.is_ok() || result.unwrap_err().kind() != ErrorKind::WouldBlock {
122        println!("Failed to drain pending events from device file");
123    }
124
125    let u_d = UninitDevice::new().unwrap();
126    let d = u_d.set_file(file).unwrap();
127
128    println!(
129        "Input device ID: bus 0x{:x} vendor 0x{:x} product 0x{:x}",
130        d.bustype(),
131        d.vendor_id(),
132        d.product_id()
133    );
134    println!("Evdev version: {:x}", d.driver_version());
135    println!("Input device name: \"{}\"", d.name().unwrap_or(""));
136    println!("Phys location: {}", d.phys().unwrap_or(""));
137    println!("Uniq identifier: {}", d.uniq().unwrap_or(""));
138
139    print_bits(&d);
140    print_props(&d);
141
142    let mut a: io::Result<(ReadStatus, InputEvent)>;
143    loop {
144        a = d.next_event(ReadFlag::NORMAL);
145        if a.is_ok() {
146            let mut result = a.ok().unwrap();
147            match result.0 {
148                ReadStatus::Sync => {
149                    println!("::::::::::::::::::::: dropped ::::::::::::::::::::::");
150                    while result.0 == ReadStatus::Sync {
151                        print_sync_dropped_event(&result.1);
152                        a = d.next_event(ReadFlag::SYNC);
153                        if a.is_ok() {
154                            result = a.ok().unwrap();
155                        } else {
156                            break;
157                        }
158                    }
159                    println!("::::::::::::::::::::: re-synced ::::::::::::::::::::");
160                }
161                ReadStatus::Success => print_event(&result.1),
162            }
163        } else {
164            let err = a.err().unwrap();
165            match err.raw_os_error() {
166                Some(libc::EAGAIN) => continue,
167                _ => {
168                    println!("{}", err);
169                    break;
170                }
171            }
172        }
173    }
174}
More examples
Hide additional examples
examples/vmouse.rs (line 35)
9fn main() -> Result<(), std::io::Error> {
10    // Parse command line arguments
11    let mut args = std::env::args();
12
13    if args.len() != 2 {
14        let n = args.nth(0).unwrap();
15        println!("Usage: `{} DEVICE`, eg. `{} /dev/input/event13`", n, n);
16        std::process::exit(1);
17    }
18
19    let device = &args.nth(1).unwrap();
20
21    // Connect to real keyboard
22    let f = File::open(device)?;
23    let d = Device::new_from_file(f)?;
24
25    if let Some(n) = d.name() {
26        println!(
27            "Connected to device: '{}' ({:04x}:{:04x})",
28            n,
29            d.vendor_id(),
30            d.product_id()
31        );
32    }
33
34    // Create virtual device
35    let u = UninitDevice::new().unwrap();
36
37    // Setup device
38    // per: https://01.org/linuxgraphics/gfx-docs/drm/input/uinput.html#mouse-movements
39
40    u.set_name("Virtual Mouse");
41    u.set_bustype(BusType::BUS_USB as u16);
42    u.set_vendor_id(0xabcd);
43    u.set_product_id(0xefef);
44
45    // Note mouse keys have to be enabled for this to be detected
46    // as a usable device, see: https://stackoverflow.com/a/64559658/6074942
47    u.enable_event_type(&EventType::EV_KEY)?;
48    u.enable_event_code(&EventCode::EV_KEY(EV_KEY::BTN_LEFT), None)?;
49    u.enable_event_code(&EventCode::EV_KEY(EV_KEY::BTN_RIGHT), None)?;
50
51    u.enable_event_type(&EventType::EV_REL)?;
52    u.enable_event_code(&EventCode::EV_REL(EV_REL::REL_X), None)?;
53    u.enable_event_code(&EventCode::EV_REL(EV_REL::REL_Y), None)?;
54
55    u.enable_event_code(&EventCode::EV_SYN(EV_SYN::SYN_REPORT), None)?;
56
57    // Attempt to create UInputDevice from UninitDevice
58    let v = UInputDevice::create_from_device(&u)?;
59
60    loop {
61        // Fetch keyboard events
62        let (_status, event) = d.next_event(ReadFlag::NORMAL | ReadFlag::BLOCKING)?;
63
64        // Map these to mouse events
65        println!("Event: {:?}", event);
66
67        // Map direction keys to mouse events
68        let e = match event.event_code {
69            EventCode::EV_KEY(EV_KEY::KEY_RIGHT) => Some((EV_REL::REL_X, MOUSE_STEP_X)),
70            EventCode::EV_KEY(EV_KEY::KEY_LEFT) => Some((EV_REL::REL_X, -MOUSE_STEP_X)),
71            EventCode::EV_KEY(EV_KEY::KEY_UP) => Some((EV_REL::REL_Y, -MOUSE_STEP_Y)),
72            EventCode::EV_KEY(EV_KEY::KEY_DOWN) => Some((EV_REL::REL_Y, MOUSE_STEP_Y)),
73            _ => None,
74        };
75
76        // Write mapped event
77        if let Some((e, n)) = e {
78            v.write_event(&InputEvent {
79                time: event.time,
80                event_code: EventCode::EV_REL(e),
81                value: n,
82            })?;
83
84            v.write_event(&InputEvent {
85                time: event.time,
86                event_code: EventCode::EV_SYN(EV_SYN::SYN_REPORT),
87                value: 0,
88            })?;
89        }
90    }
91}
Source

pub fn set_file(self, file: File) -> Result<Device>

Set the file for this struct and initialize internal data.

If the device changed and you need to re-read a device, use Device::new_from_file method. If you need to change the file after closing and re-opening the same device, use change_file.

Examples found in repository?
examples/evtest.rs (line 126)
104fn main() {
105    let mut args = std::env::args();
106
107    if args.len() != 2 {
108        usage();
109        std::process::exit(1);
110    }
111
112    let path = &args.nth(1).unwrap();
113    let mut file = OpenOptions::new()
114        .read(true)
115        .write(true)
116        .custom_flags(libc::O_NONBLOCK)
117        .open(path)
118        .unwrap();
119    let mut buffer = Vec::new();
120    let result = file.read_to_end(&mut buffer);
121    if result.is_ok() || result.unwrap_err().kind() != ErrorKind::WouldBlock {
122        println!("Failed to drain pending events from device file");
123    }
124
125    let u_d = UninitDevice::new().unwrap();
126    let d = u_d.set_file(file).unwrap();
127
128    println!(
129        "Input device ID: bus 0x{:x} vendor 0x{:x} product 0x{:x}",
130        d.bustype(),
131        d.vendor_id(),
132        d.product_id()
133    );
134    println!("Evdev version: {:x}", d.driver_version());
135    println!("Input device name: \"{}\"", d.name().unwrap_or(""));
136    println!("Phys location: {}", d.phys().unwrap_or(""));
137    println!("Uniq identifier: {}", d.uniq().unwrap_or(""));
138
139    print_bits(&d);
140    print_props(&d);
141
142    let mut a: io::Result<(ReadStatus, InputEvent)>;
143    loop {
144        a = d.next_event(ReadFlag::NORMAL);
145        if a.is_ok() {
146            let mut result = a.ok().unwrap();
147            match result.0 {
148                ReadStatus::Sync => {
149                    println!("::::::::::::::::::::: dropped ::::::::::::::::::::::");
150                    while result.0 == ReadStatus::Sync {
151                        print_sync_dropped_event(&result.1);
152                        a = d.next_event(ReadFlag::SYNC);
153                        if a.is_ok() {
154                            result = a.ok().unwrap();
155                        } else {
156                            break;
157                        }
158                    }
159                    println!("::::::::::::::::::::: re-synced ::::::::::::::::::::");
160                }
161                ReadStatus::Success => print_event(&result.1),
162            }
163        } else {
164            let err = a.err().unwrap();
165            match err.raw_os_error() {
166                Some(libc::EAGAIN) => continue,
167                _ => {
168                    println!("{}", err);
169                    break;
170                }
171            }
172        }
173    }
174}
Source

pub fn set_fd(self, file: File) -> Result<Device>

👎Deprecated since 0.5.0: Prefer set_file. Some function names were changed so they more closely match their type signature. See issue 42 for discussion https://github.com/ndesh26/evdev-rs/issues/42

Trait Implementations§

Source§

impl Debug for UninitDevice

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl DeviceWrapper for UninitDevice

Source§

fn raw(&self) -> *mut libevdev

Source§

fn enable<E: Enable>(&self, e: E) -> Result<()>

Forcibly enable an EventType/InputProp on this device, even if the underlying device does not support it. While this cannot make the device actually report such events, it will now return true for has(). Read more
Source§

fn enable_property(&self, prop: &InputProp) -> Result<()>

Enables this property, a call to set_file will overwrite any previously set values Read more
Source§

fn enable_event_type(&self, ev_type: &EventType) -> Result<()>

Forcibly enable an event type on this device, even if the underlying device does not support it. While this cannot make the device actually report such events, it will now return true for libevdev_has_event_type(). Read more
Source§

fn enable_event_code( &self, ev_code: &EventCode, data: Option<EnableCodeData>, ) -> Result<()>

Forcibly enable an event type on this device, even if the underlying device does not support it. While this cannot make the device actually report such events, it will now return true for libevdev_has_event_code(). Read more
Source§

fn disable<E: Enable>(&self, d: E) -> Result<()>

Forcibly disable an EventType/EventCode on this device, even if the underlying device provides it. This effectively mutes the respective set of events. has() will return false for this EventType/EventCode Read more
Source§

fn disable_event_type(&self, ev_type: &EventType) -> Result<()>

Forcibly disable an event type on this device, even if the underlying device provides it. This effectively mutes the respective set of events. libevdev will filter any events matching this type and none will reach the caller. libevdev_has_event_type() will return false for this type. Read more
Source§

fn disable_event_code(&self, code: &EventCode) -> Result<()>

Forcibly disable an event code on this device, even if the underlying device provides it. This effectively mutes the respective set of events. libevdev will filter any events matching this type and code and none will reach the caller. has_event_code will return false for this code. Read more
Source§

fn has<E: Enable>(&self, e: E) -> bool

Returns true if device support the InputProp/EventType/EventCode and false otherwise
Source§

fn has_property(&self, prop: &InputProp) -> bool

Returns true if device support the property and false otherwise Read more
Source§

fn has_event_type(&self, ev_type: &EventType) -> bool

Returns true is the device support this event type and false otherwise Read more
Source§

fn has_event_code(&self, code: &EventCode) -> bool

Return true is the device support this event type and code and false otherwise Read more
Source§

fn name(&self) -> Option<&str>

Get device’s name, as set by the kernel, or overridden by a call to set_name
Source§

fn phys(&self) -> Option<&str>

Get device’s physical location, as set by the kernel, or overridden by a call to set_phys
Source§

fn uniq(&self) -> Option<&str>

Get device’s unique identifier, as set by the kernel, or overridden by a call to set_uniq
Source§

fn set_name(&self, field: &str)

Source§

fn set_phys(&self, field: &str)

Source§

fn set_uniq(&self, field: &str)

Source§

fn product_id(&self) -> u16

Source§

fn vendor_id(&self) -> u16

Source§

fn bustype(&self) -> u16

Source§

fn version(&self) -> u16

Source§

fn set_product_id(&self, field: u16)

Source§

fn set_vendor_id(&self, field: u16)

Source§

fn set_bustype(&self, field: u16)

Source§

fn set_version(&self, field: u16)

Source§

fn abs_info(&self, code: &EventCode) -> Option<AbsInfo>

Get the axis info for the given axis, as advertised by the kernel. Read more
Source§

fn set_abs_info(&self, code: &EventCode, absinfo: &AbsInfo)

Change the abs info for the given EV_ABS event code, if the code exists. Read more
Source§

fn event_value(&self, code: &EventCode) -> Option<i32>

Returns the current value of the event type. Read more
Source§

fn set_event_value(&self, code: &EventCode, val: i32) -> Result<()>

Set the value for a given event type and code. Read more
Source§

fn abs_minimum(&self, code: u32) -> Result<i32>

Source§

fn abs_maximum(&self, code: u32) -> Result<i32>

Source§

fn abs_fuzz(&self, code: u32) -> Result<i32>

Source§

fn abs_flat(&self, code: u32) -> Result<i32>

Source§

fn abs_resolution(&self, code: u32) -> Result<i32>

Source§

fn set_abs_minimum(&self, code: u32, val: i32)

Source§

fn set_abs_maximum(&self, code: u32, val: i32)

Source§

fn set_abs_fuzz(&self, code: u32, val: i32)

Source§

fn set_abs_flat(&self, code: u32, val: i32)

Source§

fn set_abs_resolution(&self, code: u32, val: i32)

Source§

fn slot_value(&self, slot: u32, code: &EventCode) -> Option<i32>

Return the current value of the code for the given slot. Read more
Source§

fn set_slot_value(&self, slot: u32, code: &EventCode, val: i32) -> Result<()>

Set the value for a given code for the given slot. Read more
Source§

fn num_slots(&self) -> Option<i32>

Get the number of slots supported by this device. Read more
Source§

fn current_slot(&self) -> Option<i32>

Get the currently active slot. Read more
Source§

impl Drop for UninitDevice

Source§

fn drop(&mut self)

Executes the destructor for this type. Read more
Source§

impl Send for UninitDevice

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.