Skip to content

Commit

Permalink
Add UsbDeviceHandler for #7
Browse files Browse the repository at this point in the history
  • Loading branch information
jiegec committed Feb 1, 2023
1 parent 11df5fb commit 84b8d9d
Showing 1 changed file with 41 additions and 0 deletions.
41 changes: 41 additions & 0 deletions src/device.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ pub struct UsbDevice {
pub configuration_value: u8,
pub num_configurations: u8,
pub interfaces: Vec<UsbInterface>,
pub device_handler: Option<Arc<Mutex<Box<dyn UsbDeviceHandler + Send>>>>,
pub(crate) ep0_in: UsbEndpoint,
pub(crate) ep0_out: UsbEndpoint,
// strings
Expand Down Expand Up @@ -81,6 +82,14 @@ impl UsbDevice {
self
}

pub fn with_device_handler(
mut self,
handler: Arc<Mutex<Box<dyn UsbDeviceHandler + Send>>>,
) -> Self {
self.device_handler = Some(handler);
self
}

pub(crate) fn new_string(&mut self, s: &str) -> u8 {
for i in 1.. {
if self.string_pool.get(&i).is_none() {
Expand Down Expand Up @@ -353,6 +362,13 @@ impl UsbDevice {
let resp = handler.handle_urb(intf, ep, setup_packet, &out_data)?;
return Ok(resp);
}
_ if setup_packet.request_type & 0xF == 0 && self.device_handler.is_some() => {
// to device
// see https://www.beyondlogic.org/usbnutshell/usb6.shtml
let lock = self.device_handler.as_ref().unwrap();
let mut handler = lock.lock().unwrap();
return Ok(handler.handle_urb(setup_packet, &out_data)?);
}
_ => unimplemented!("control in"),
}
}
Expand Down Expand Up @@ -383,6 +399,13 @@ impl UsbDevice {
let resp = handler.handle_urb(intf, ep, setup_packet, &out_data)?;
return Ok(resp);
}
_ if setup_packet.request_type & 0xF == 0 && self.device_handler.is_some() => {
// to device
// see https://www.beyondlogic.org/usbnutshell/usb6.shtml
let lock = self.device_handler.as_ref().unwrap();
let mut handler = lock.lock().unwrap();
return Ok(handler.handle_urb(setup_packet, &out_data)?);
}
_ => unimplemented!("control out"),
}
}
Expand All @@ -397,3 +420,21 @@ impl UsbDevice {
}
}
}

/// A handler for URB targeting the device
pub trait UsbDeviceHandler {
/// Handle a URB(USB Request Block) targeting at this device
///
/// When the lower 4 bits of bmRequestType is zero and the URB is not handled by the library, this function is called
fn handle_urb(&mut self, setup: SetupPacket, req: &[u8]) -> Result<Vec<u8>>;

/// Helper to downcast to actual struct
///
/// Please implement it as:
/// ```ignore
/// fn as_any(&mut self) -> &mut dyn Any {
/// self
/// }
/// ```
fn as_any(&mut self) -> &mut dyn Any;
}

0 comments on commit 84b8d9d

Please sign in to comment.