1use crate::protocol_helpers::prelude::*;
25use super::super::all_types::*;
26
27pub struct WlRegistry {
31 core: ObjectCore,
32 handler: HandlerHolder<dyn WlRegistryHandler>,
33 names: RefCell<HashSet<u32>>,
34}
35
36struct DefaultHandler;
37
38impl WlRegistryHandler for DefaultHandler { }
39
40impl ConcreteObject for WlRegistry {
41 const XML_VERSION: u32 = 1;
42 const INTERFACE: ObjectInterface = ObjectInterface::WlRegistry;
43 const INTERFACE_NAME: &str = "wl_registry";
44}
45
46impl WlRegistry {
47 pub fn set_handler(&self, handler: impl WlRegistryHandler) {
49 self.set_boxed_handler(Box::new(handler));
50 }
51
52 pub fn set_boxed_handler(&self, handler: Box<dyn WlRegistryHandler>) {
54 if self.core.state.destroyed.get() {
55 return;
56 }
57 self.handler.set(Some(handler));
58 }
59}
60
61impl Debug for WlRegistry {
62 fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
63 f.debug_struct("WlRegistry")
64 .field("server_obj_id", &self.core.server_obj_id.get())
65 .field("client_id", &self.core.client_id.get())
66 .field("client_obj_id", &self.core.client_obj_id.get())
67 .finish()
68 }
69}
70
71impl WlRegistry {
72 pub const MSG__BIND__SINCE: u32 = 1;
74
75 #[inline]
85 pub fn try_send_bind(
86 &self,
87 name: u32,
88 id: Rc<dyn Object>,
89 ) -> Result<(), ObjectError> {
90 let (
91 arg0,
92 arg1,
93 ) = (
94 name,
95 id,
96 );
97 let arg1_obj = arg1;
98 let arg1 = arg1_obj.core();
99 let core = self.core();
100 let Some(id) = core.server_obj_id.get() else {
101 return Err(ObjectError(ObjectErrorKind::ReceiverNoServerId));
102 };
103 arg1.generate_server_id(arg1_obj.clone())
104 .map_err(|e| ObjectError(ObjectErrorKind::GenerateServerId("id", e)))?;
105 let arg1_id = arg1.server_obj_id.get().unwrap_or(0);
106 #[cfg(feature = "logging")]
107 if self.core.state.log {
108 #[cold]
109 fn log(state: &State, id: u32, arg0: u32, arg1_interface: &str, arg1_id: u32, arg1_version: u32) {
110 let (millis, micros) = time_since_epoch();
111 let prefix = &state.log_prefix;
112 let args = format_args!("[{millis:7}.{micros:03}] {prefix}server <= wl_registry#{}.bind(name: {}, id: {}#{} (version: {}))\n", id, arg0, arg1_interface, arg1_id, arg1_version);
113 state.log(args);
114 }
115 log(&self.core.state, id, arg0, arg1.interface.name(), arg1_id, arg1.version);
116 }
117 let Some(endpoint) = &self.core.state.server else {
118 return Ok(());
119 };
120 if !endpoint.flush_queued.replace(true) {
121 self.core.state.add_flushable_endpoint(endpoint, None);
122 }
123 let mut outgoing_ref = endpoint.outgoing.borrow_mut();
124 let outgoing = &mut *outgoing_ref;
125 let mut fmt = outgoing.formatter();
126 fmt.words([
127 id,
128 0,
129 arg0,
130 ]);
131 fmt.string(arg1.interface.name());
132 fmt.words([
133 arg1.version,
134 arg1_id,
135 ]);
136 Ok(())
137 }
138
139 #[inline]
149 pub fn send_bind(
150 &self,
151 name: u32,
152 id: Rc<dyn Object>,
153 ) {
154 let res = self.try_send_bind(
155 name,
156 id,
157 );
158 if let Err(e) = res {
159 log_send("wl_registry.bind", &e);
160 }
161 }
162
163 pub const MSG__GLOBAL__SINCE: u32 = 1;
165
166 #[inline]
180 pub fn try_send_global(
181 &self,
182 name: u32,
183 interface: ObjectInterface,
184 version: u32,
185 ) -> Result<(), ObjectError> {
186 let interface = interface.name();
187 let (
188 arg0,
189 arg1,
190 arg2,
191 ) = (
192 name,
193 interface,
194 version,
195 );
196 let core = self.core();
197 let client_ref = core.client.borrow();
198 let Some(client) = &*client_ref else {
199 return Err(ObjectError(ObjectErrorKind::ReceiverNoClient));
200 };
201 let id = core.client_obj_id.get().unwrap_or(0);
202 #[cfg(feature = "logging")]
203 if self.core.state.log {
204 #[cold]
205 fn log(state: &State, client_id: u64, id: u32, arg0: u32, arg1: &str, arg2: u32) {
206 let (millis, micros) = time_since_epoch();
207 let prefix = &state.log_prefix;
208 let args = format_args!("[{millis:7}.{micros:03}] {prefix}client#{:<4} <= wl_registry#{}.global(name: {}, interface: {:?}, version: {})\n", client_id, id, arg0, arg1, arg2);
209 state.log(args);
210 }
211 log(&self.core.state, client.endpoint.id, id, arg0, arg1, arg2);
212 }
213 let endpoint = &client.endpoint;
214 if !endpoint.flush_queued.replace(true) {
215 self.core.state.add_flushable_endpoint(endpoint, Some(client));
216 }
217 let mut outgoing_ref = endpoint.outgoing.borrow_mut();
218 let outgoing = &mut *outgoing_ref;
219 let mut fmt = outgoing.formatter();
220 fmt.words([
221 id,
222 0,
223 arg0,
224 ]);
225 fmt.string(arg1);
226 fmt.words([
227 arg2,
228 ]);
229 Ok(())
230 }
231
232 #[inline]
246 pub fn send_global(
247 &self,
248 name: u32,
249 interface: ObjectInterface,
250 version: u32,
251 ) {
252 let res = self.try_send_global(
253 name,
254 interface,
255 version,
256 );
257 if let Err(e) = res {
258 log_send("wl_registry.global", &e);
259 }
260 }
261
262 pub const MSG__GLOBAL_REMOVE__SINCE: u32 = 1;
264
265 #[inline]
282 pub fn try_send_global_remove(
283 &self,
284 name: u32,
285 ) -> Result<(), ObjectError> {
286 let (
287 arg0,
288 ) = (
289 name,
290 );
291 let core = self.core();
292 let client_ref = core.client.borrow();
293 let Some(client) = &*client_ref else {
294 return Err(ObjectError(ObjectErrorKind::ReceiverNoClient));
295 };
296 let id = core.client_obj_id.get().unwrap_or(0);
297 #[cfg(feature = "logging")]
298 if self.core.state.log {
299 #[cold]
300 fn log(state: &State, client_id: u64, id: u32, arg0: u32) {
301 let (millis, micros) = time_since_epoch();
302 let prefix = &state.log_prefix;
303 let args = format_args!("[{millis:7}.{micros:03}] {prefix}client#{:<4} <= wl_registry#{}.global_remove(name: {})\n", client_id, id, arg0);
304 state.log(args);
305 }
306 log(&self.core.state, client.endpoint.id, id, arg0);
307 }
308 let endpoint = &client.endpoint;
309 if !endpoint.flush_queued.replace(true) {
310 self.core.state.add_flushable_endpoint(endpoint, Some(client));
311 }
312 let mut outgoing_ref = endpoint.outgoing.borrow_mut();
313 let outgoing = &mut *outgoing_ref;
314 let mut fmt = outgoing.formatter();
315 fmt.words([
316 id,
317 1,
318 arg0,
319 ]);
320 Ok(())
321 }
322
323 #[inline]
340 pub fn send_global_remove(
341 &self,
342 name: u32,
343 ) {
344 let res = self.try_send_global_remove(
345 name,
346 );
347 if let Err(e) = res {
348 log_send("wl_registry.global_remove", &e);
349 }
350 }
351}
352
353pub trait WlRegistryHandler: Any {
355 #[inline]
359 fn delete_id(&mut self, slf: &Rc<WlRegistry>) {
360 slf.core.delete_id();
361 }
362
363 #[inline]
373 fn handle_bind(
374 &mut self,
375 slf: &Rc<WlRegistry>,
376 name: u32,
377 id: Rc<dyn Object>,
378 ) {
379 if !slf.core.forward_to_server.get() {
380 return;
381 }
382 let res = slf.try_send_bind(
383 name,
384 id,
385 );
386 if let Err(e) = res {
387 log_forward("wl_registry.bind", &e);
388 }
389 }
390
391 #[inline]
405 fn handle_global(
406 &mut self,
407 slf: &Rc<WlRegistry>,
408 name: u32,
409 interface: ObjectInterface,
410 version: u32,
411 ) {
412 if !slf.core.forward_to_client.get() {
413 return;
414 }
415 let res = slf.try_send_global(
416 name,
417 interface,
418 version,
419 );
420 if let Err(e) = res {
421 log_forward("wl_registry.global", &e);
422 }
423 }
424
425 #[inline]
442 fn handle_global_remove(
443 &mut self,
444 slf: &Rc<WlRegistry>,
445 name: u32,
446 ) {
447 if !slf.core.forward_to_client.get() {
448 return;
449 }
450 let res = slf.try_send_global_remove(
451 name,
452 );
453 if let Err(e) = res {
454 log_forward("wl_registry.global_remove", &e);
455 }
456 }
457}
458
459impl ObjectPrivate for WlRegistry {
460 fn new(state: &Rc<State>, version: u32) -> Rc<Self> {
461 Rc::<Self>::new_cyclic(|slf| Self {
462 core: ObjectCore::new(state, slf.clone(), ObjectInterface::WlRegistry, version),
463 handler: Default::default(),
464 names: Default::default(),
465 })
466 }
467
468 fn delete_id(self: Rc<Self>) -> Result<(), (ObjectError, Rc<dyn Object>)> {
469 let Some(mut handler) = self.handler.try_borrow_mut() else {
470 return Err((ObjectError(ObjectErrorKind::HandlerBorrowed), self));
471 };
472 if let Some(handler) = &mut *handler {
473 handler.delete_id(&self);
474 } else {
475 self.core.delete_id();
476 }
477 Ok(())
478 }
479
480 fn handle_request(self: Rc<Self>, client: &Rc<Client>, msg: &[u32], fds: &mut VecDeque<Rc<OwnedFd>>) -> Result<(), ObjectError> {
481 let Some(mut handler) = self.handler.try_borrow_mut() else {
482 return Err(ObjectError(ObjectErrorKind::HandlerBorrowed));
483 };
484 let handler = &mut *handler;
485 match msg[1] & 0xffff {
486 0 => {
487 let mut offset = 2;
488 let Some(&arg0) = msg.get(offset) else {
489 return Err(ObjectError(ObjectErrorKind::MissingArgument("name")));
490 };
491 offset += 1;
492 let arg1_interface;
493 (arg1_interface, offset) = parse_string::<NonNullString>(msg, offset, "id")?;
494 let Some(&arg1_version) = msg.get(offset) else {
495 return Err(ObjectError(ObjectErrorKind::MissingArgument("id")));
496 };
497 offset += 1;
498 let Some(&arg1) = msg.get(offset) else {
499 return Err(ObjectError(ObjectErrorKind::MissingArgument("id")));
500 };
501 offset += 1;
502 if offset != msg.len() {
503 return Err(ObjectError(ObjectErrorKind::TrailingBytes));
504 }
505 #[cfg(feature = "logging")]
506 if self.core.state.log {
507 #[cold]
508 fn log(state: &State, client_id: u64, id: u32, arg0: u32, arg1_interface: &str, arg1_id: u32, arg1_version: u32) {
509 let (millis, micros) = time_since_epoch();
510 let prefix = &state.log_prefix;
511 let args = format_args!("[{millis:7}.{micros:03}] {prefix}client#{:<4} -> wl_registry#{}.bind(name: {}, id: {}#{} (version: {}))\n", client_id, id, arg0, arg1_interface, arg1_id, arg1_version);
512 state.log(args);
513 }
514 log(&self.core.state, client.endpoint.id, msg[0], arg0, arg1_interface, arg1, arg1_version);
515 }
516 let arg1_id = arg1;
517 let arg1 = create_object_for_interface(&self.core.state, arg1_interface, arg1_version)?;
518 arg1.core().set_client_id(client, arg1_id, arg1.clone())
519 .map_err(|e| ObjectError(ObjectErrorKind::SetClientId(arg1_id, "id", e)))?;
520 if let Some(handler) = handler {
521 (**handler).handle_bind(&self, arg0, arg1);
522 } else {
523 DefaultHandler.handle_bind(&self, arg0, arg1);
524 }
525 }
526 n => {
527 let _ = client;
528 let _ = msg;
529 let _ = fds;
530 let _ = handler;
531 return Err(ObjectError(ObjectErrorKind::UnknownMessageId(n)));
532 }
533 }
534 Ok(())
535 }
536
537 fn handle_event(self: Rc<Self>, server: &Endpoint, msg: &[u32], fds: &mut VecDeque<Rc<OwnedFd>>) -> Result<(), ObjectError> {
538 let Some(mut handler) = self.handler.try_borrow_mut() else {
539 return Err(ObjectError(ObjectErrorKind::HandlerBorrowed));
540 };
541 let handler = &mut *handler;
542 match msg[1] & 0xffff {
543 0 => {
544 let mut offset = 2;
545 let Some(&arg0) = msg.get(offset) else {
546 return Err(ObjectError(ObjectErrorKind::MissingArgument("name")));
547 };
548 offset += 1;
549 let arg1;
550 (arg1, offset) = parse_string::<NonNullString>(msg, offset, "interface")?;
551 let Some(&arg2) = msg.get(offset) else {
552 return Err(ObjectError(ObjectErrorKind::MissingArgument("version")));
553 };
554 offset += 1;
555 if offset != msg.len() {
556 return Err(ObjectError(ObjectErrorKind::TrailingBytes));
557 }
558 #[cfg(feature = "logging")]
559 if self.core.state.log {
560 #[cold]
561 fn log(state: &State, id: u32, arg0: u32, arg1: &str, arg2: u32) {
562 let (millis, micros) = time_since_epoch();
563 let prefix = &state.log_prefix;
564 let args = format_args!("[{millis:7}.{micros:03}] {prefix}server -> wl_registry#{}.global(name: {}, interface: {:?}, version: {})\n", id, arg0, arg1, arg2);
565 state.log(args);
566 }
567 log(&self.core.state, msg[0], arg0, arg1, arg2);
568 }
569 let Some(arg1) = ObjectInterface::from_str(arg1) else {
570 return Ok(());
571 };
572 let max_version = self.core.state.baseline.1[arg1];
573 if max_version == 0 {
574 return Ok(());
575 }
576 self.names.borrow_mut().insert(arg0);
577 let arg2 = max_version.min(arg2);
578 if let Some(handler) = handler {
579 (**handler).handle_global(&self, arg0, arg1, arg2);
580 } else {
581 DefaultHandler.handle_global(&self, arg0, arg1, arg2);
582 }
583 }
584 1 => {
585 let [
586 arg0,
587 ] = msg[2..] else {
588 return Err(ObjectError(ObjectErrorKind::WrongMessageSize(msg.len() as u32 * 4, 12)));
589 };
590 #[cfg(feature = "logging")]
591 if self.core.state.log {
592 #[cold]
593 fn log(state: &State, id: u32, arg0: u32) {
594 let (millis, micros) = time_since_epoch();
595 let prefix = &state.log_prefix;
596 let args = format_args!("[{millis:7}.{micros:03}] {prefix}server -> wl_registry#{}.global_remove(name: {})\n", id, arg0);
597 state.log(args);
598 }
599 log(&self.core.state, msg[0], arg0);
600 }
601 if !self.names.borrow_mut().remove(&arg0) {
602 return Ok(());
603 }
604 if let Some(handler) = handler {
605 (**handler).handle_global_remove(&self, arg0);
606 } else {
607 DefaultHandler.handle_global_remove(&self, arg0);
608 }
609 }
610 n => {
611 let _ = server;
612 let _ = msg;
613 let _ = fds;
614 let _ = handler;
615 return Err(ObjectError(ObjectErrorKind::UnknownMessageId(n)));
616 }
617 }
618 Ok(())
619 }
620
621 fn get_request_name(&self, id: u32) -> Option<&'static str> {
622 let name = match id {
623 0 => "bind",
624 _ => return None,
625 };
626 Some(name)
627 }
628
629 fn get_event_name(&self, id: u32) -> Option<&'static str> {
630 let name = match id {
631 0 => "global",
632 1 => "global_remove",
633 _ => return None,
634 };
635 Some(name)
636 }
637}
638
639impl Object for WlRegistry {
640 fn core(&self) -> &ObjectCore {
641 &self.core
642 }
643
644 fn unset_handler(&self) {
645 self.handler.set(None);
646 }
647
648 fn get_handler_any_ref(&self) -> Result<HandlerRef<'_, dyn Any>, HandlerAccessError> {
649 let borrowed = self.handler.try_borrow().ok_or(HandlerAccessError::AlreadyBorrowed)?;
650 if borrowed.is_none() {
651 return Err(HandlerAccessError::NoHandler);
652 }
653 Ok(HandlerRef::map(borrowed, |handler| &**handler.as_ref().unwrap() as &dyn Any))
654 }
655
656 fn get_handler_any_mut(&self) -> Result<HandlerMut<'_, dyn Any>, HandlerAccessError> {
657 let borrowed = self.handler.try_borrow_mut().ok_or(HandlerAccessError::AlreadyBorrowed)?;
658 if borrowed.is_none() {
659 return Err(HandlerAccessError::NoHandler);
660 }
661 Ok(HandlerMut::map(borrowed, |handler| &mut **handler.as_mut().unwrap() as &mut dyn Any))
662 }
663}
664