1use std::{
4 net::{SocketAddr, UdpSocket},
5 sync::Arc,
6 thread::{self, JoinHandle},
7};
8
9use crate::{
10 address::NodeId,
11 buffer::NetBufferProducer,
12 clock::ClockSync,
13 error::{NetError, Result},
14 osc::parser::parse_osc_message,
15};
16
17pub struct OscServerConfig {
19 pub bind_addr: SocketAddr,
21 pub node_id: NodeId,
23 pub recv_buffer_size: usize,
25}
26
27impl Default for OscServerConfig {
28 fn default() -> Self {
29 Self {
30 bind_addr: "0.0.0.0:9000".parse().unwrap(),
31 node_id: NodeId::default(),
32 recv_buffer_size: 1024,
33 }
34 }
35}
36
37pub struct OscServer {
42 config: OscServerConfig,
43 producer: NetBufferProducer,
44 clock_sync: Arc<ClockSync>,
45}
46
47impl OscServer {
48 pub fn new(config: OscServerConfig, producer: NetBufferProducer) -> Self {
55 Self {
56 config,
57 producer,
58 clock_sync: Arc::new(ClockSync::new()),
59 }
60 }
61
62 pub fn with_defaults(producer: NetBufferProducer) -> Self {
64 Self::new(OscServerConfig::default(), producer)
65 }
66
67 pub fn clock(&self) -> Arc<ClockSync> {
69 Arc::clone(&self.clock_sync)
70 }
71
72 pub fn run(mut self) -> Result<()> {
77 let socket = UdpSocket::bind(self.config.bind_addr)?;
78 let mut buf = vec![0u8; self.config.recv_buffer_size];
79
80 loop {
81 match socket.recv_from(&mut buf) {
82 Ok((len, src_addr)) => {
83 self.handle_packet(&buf[..len], src_addr);
84 }
85 Err(e) => {
86 if e.kind() != std::io::ErrorKind::WouldBlock {
87 return Err(NetError::IoError);
88 }
89 }
90 }
91 }
92 }
93
94 pub fn spawn(self) -> JoinHandle<Result<()>> {
99 thread::spawn(move || self.run())
100 }
101
102 fn handle_packet(&mut self, data: &[u8], _src_addr: SocketAddr) {
103 let source_node_id = self.config.node_id;
104
105 if let Ok(messages) = parse_osc_message(data, source_node_id) {
106 for mut msg in messages {
107 msg.timestamp = self.clock_sync.now();
108
109 let _ = self.producer.try_send(msg);
110 }
111 }
112 }
113}
114
115#[cfg(test)]
116mod tests {
117 use super::*;
118 use crate::buffer::net_buffer;
119
120 #[test]
121 fn test_osc_server_config_default() {
122 let config = OscServerConfig::default();
123 assert_eq!(config.bind_addr.port(), 9000);
124 assert_eq!(config.recv_buffer_size, 1024);
125 }
126
127 #[test]
128 fn test_osc_server_creation() {
129 let (producer, _consumer) = net_buffer(64);
130 let server = OscServer::with_defaults(producer);
131 assert!(Arc::strong_count(&server.clock_sync) >= 1);
132 }
133}