Files
otd-ipc-rs/src/lib.rs

70 lines
2.0 KiB
Rust

mod messages;
mod metadata;
pub use messages::*;
use std::{
io::{Read, Write},
os::unix::net::UnixStream,
};
use crate::metadata::OtdIpcMetadata;
pub struct OtdIpc {
stream: UnixStream,
}
impl OtdIpc {
pub fn new(name: &str, version: &str) -> Result<Self, Box<dyn std::error::Error>> {
let meta = OtdIpcMetadata::new()?;
let mut stream = UnixStream::connect(meta.socket)?;
let hello = Hello::new(
0x022026020501,
name,
version,
&format!("{}.{}", slug::slugify(name), meta.id),
1,
)?;
stream.write_all(&Vec::from(hello))?;
Ok(Self { stream })
}
}
impl Iterator for OtdIpc {
type Item = Message;
fn next(&mut self) -> Option<Self::Item> {
let mut raw_header = [0; size_of::<Header>()];
self.stream.read_exact(&mut raw_header).unwrap();
let header: Header = raw_header[..].try_into().unwrap();
let mut raw_buffer = vec![0; (header.size as usize) - size_of::<Header>()];
self.stream.read_exact(&mut raw_buffer).unwrap();
match header.message_type {
messages::MessageType::None => None,
messages::MessageType::DeviceInfo => Some(Message::DeviceInfo(Box::new(
DeviceInfo::try_from(&raw_buffer[..]).unwrap(),
))),
messages::MessageType::State => {
Some(Message::State(State::try_from(&raw_buffer[..]).unwrap()))
}
messages::MessageType::Ping => {
Some(Message::Ping(Ping::try_from(&raw_buffer[..]).unwrap()))
}
messages::MessageType::DebugMessage => {
Some(Message::DebugMessage(DebugMessage::from(&raw_buffer[..])))
}
messages::MessageType::Experimental => {
Some(Message::Experimental(Experimental::from(&raw_buffer[..])))
}
messages::MessageType::Hello => {
Some(Message::Hello(Hello::try_from(&raw_buffer[..]).unwrap()))
}
}
}
}