1use alloc::{borrow::ToOwned as _, sync::Arc};
2use core::fmt;
3
4use crate::{
5 hub::{Hub, HubReport},
6 instance::{Instance, Surface},
7 registry::{Registry, RegistryReport},
8 resource_log,
9};
10
11#[derive(Debug, PartialEq, Eq)]
12pub struct GlobalReport {
13 pub surfaces: RegistryReport,
14 pub hub: HubReport,
15}
16
17impl GlobalReport {
18 pub fn surfaces(&self) -> &RegistryReport {
19 &self.surfaces
20 }
21 pub fn hub_report(&self) -> &HubReport {
22 &self.hub
23 }
24}
25
26pub struct Global {
27 pub(crate) surfaces: Registry<Arc<Surface>>,
28 pub(crate) hub: Hub,
29 pub instance: Instance,
31}
32
33impl Global {
34 pub fn new(
35 name: &str,
36 instance_desc: &wgt::InstanceDescriptor,
37 telemetry: Option<hal::Telemetry>,
38 ) -> Self {
39 profiling::scope!("Global::new");
40 Self {
41 instance: Instance::new(name, instance_desc, telemetry),
42 surfaces: Registry::new(),
43 hub: Hub::new(),
44 }
45 }
46
47 pub unsafe fn from_hal_instance<A: hal::Api>(name: &str, hal_instance: A::Instance) -> Self {
51 profiling::scope!("Global::new");
52
53 Self {
54 instance: Instance::from_hal_instance::<A>(name.to_owned(), hal_instance),
55 surfaces: Registry::new(),
56 hub: Hub::new(),
57 }
58 }
59
60 pub unsafe fn instance_as_hal<A: hal::Api>(&self) -> Option<&A::Instance> {
64 unsafe { self.instance.as_hal::<A>() }
65 }
66
67 pub unsafe fn from_instance(instance: Instance) -> Self {
71 profiling::scope!("Global::new");
72 Self {
73 instance,
74 surfaces: Registry::new(),
75 hub: Hub::new(),
76 }
77 }
78
79 pub fn generate_report(&self) -> GlobalReport {
80 GlobalReport {
81 surfaces: self.surfaces.generate_report(),
82 hub: self.hub.generate_report(),
83 }
84 }
85}
86
87impl fmt::Debug for Global {
88 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
89 f.debug_struct("Global").finish()
90 }
91}
92
93impl Drop for Global {
94 fn drop(&mut self) {
95 profiling::scope!("Global::drop");
96 resource_log!("Global::drop");
97 }
98}
99
100#[cfg(send_sync)]
101fn _test_send_sync(global: &Global) {
102 fn test_internal<T: Send + Sync>(_: T) {}
103 test_internal(global)
104}