Receiving notifications despite a filter
joelreymont opened this issue · 3 comments
I set up a vid/pid filter expecting ctx.handle_events
not to return unless a notification for my device of choice is received.
I receive connect/disconnect
notifications for any device that's attached or detached, though.
Is there a bug in the code or am I supposed to manually figure out if my device was attached or detached, like I'm doing below?
In other words, how do I wait for my device to appear or disappear without polling for it?
if rusb::has_hotplug() {
let ctx = Context::new()?;
let mut reg = Some(
HotplugBuilder::new()
.enumerate(true)
.vendor_id(args.vid)
.product_id(args.pid)
.register(&ctx, Box::new(HotPlugHandler {}))?,
);
loop {
ctx.handle_events(None).unwrap();
if is_connected(ctx.devices(), args.vid, args.pid) {
if let Some(reg) = reg.take() {
ctx.unregister_callback(reg);
break;
}
}
}
I can't reproduce you problem. What linux distro do you use?
use rusb::{Context, Device, HotplugBuilder, UsbContext};
struct HotPlugHandler;
impl<T: UsbContext> rusb::Hotplug<T> for HotPlugHandler {
fn device_arrived(&mut self, device: Device<T>) {
println!("device arrived {:?}", device);
}
fn device_left(&mut self, device: Device<T>) {
println!("device left {:?}", device);
}
}
impl Drop for HotPlugHandler {
fn drop(&mut self) {
println!("HotPlugHandler dropped");
}
}
fn main() -> rusb::Result<()> {
if rusb::has_hotplug() {
let context = Context::new()?;
let mut reg: Option<rusb::Registration<Context>> = Some(
HotplugBuilder::new()
.enumerate(true)
.vendor_id(0x18d1)
.product_id(0x4ee7)
.register(&context, Box::new(HotPlugHandler {}))?,
);
loop {
context.handle_events(None).unwrap();
}
Ok(())
} else {
eprint!("libusb hotplug api unsupported");
Ok(())
}
}
I tested this on MacOS Venture (13.0.1) as well as Ubuntu 22.10.
Please change the code in the loop to look like this and you may see what I'm complaining about:
context.handle_events(None).unwrap();
if let Some(reg) = reg.take() {
ctx.unregister_callback(reg);
break;
}
You should see context.handle_events
returning for any device inserted or removed, not just the ones you are filtering for. If that's correct behavior then how do I wait for my device events without polling?
There are operations that should not be performed in the callbacks and it would be natural to wait for a device in the loop and then perform any necessary operations once the device was attached or detached.
This is expected behavioral. handle_events
just handle any events. You should run it in separate thread.
If you wand get you device look at this example #100 (comment)