use core::fmt;
pub type HidResult<T> = Result<T, HidError>;
#[derive(Debug)]
#[non_exhaustive]
pub enum HidError {
Initialization {
message: String,
},
DeviceNotFound,
OpenFailed {
message: String,
},
#[cfg(not(target_arch = "wasm32"))]
Io {
operation: &'static str,
source: std::io::Error,
},
Disconnected,
InvalidData {
message: String,
},
Parse {
message: String,
},
Unsupported {
message: String,
},
Backend {
message: String,
},
}
impl HidError {
pub(crate) fn backend(message: impl Into<String>) -> Self {
HidError::Backend {
message: message.into(),
}
}
}
impl fmt::Display for HidError {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
match self {
HidError::Initialization { message } => {
write!(f, "failed to initialize HID backend: {message}")
}
HidError::DeviceNotFound => write!(f, "device not found"),
HidError::OpenFailed { message } => write!(f, "failed to open device: {message}"),
#[cfg(not(target_arch = "wasm32"))]
HidError::Io { operation, source } => write!(f, "{operation}: {source}"),
HidError::Disconnected => write!(f, "device disconnected"),
HidError::InvalidData { message } => write!(f, "invalid data: {message}"),
HidError::Parse { message } => write!(f, "parse error: {message}"),
HidError::Unsupported { message } => write!(f, "unsupported operation: {message}"),
HidError::Backend { message } => write!(f, "{message}"),
}
}
}
impl std::error::Error for HidError {
fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
match self {
#[cfg(not(target_arch = "wasm32"))]
HidError::Io { source, .. } => Some(source),
_ => None,
}
}
}
#[cfg(not(target_arch = "wasm32"))]
impl HidError {
pub(crate) fn io(operation: &'static str, source: std::io::Error) -> Self {
HidError::Io { operation, source }
}
#[allow(dead_code)]
pub(crate) fn last_os_error(operation: &'static str) -> Self {
HidError::Io {
operation,
source: std::io::Error::last_os_error(),
}
}
}