Skip to main content

micromegas_tracing/metrics/
block.rs

1use super::{TaggedFloatMetricEvent, TaggedIntegerMetricEvent};
2use crate::{
3    dyn_deps::DynDeps,
4    event::{EventBlock, EventStream, ExtractDeps},
5    metrics::{
6        FloatMetricEvent, IntegerMetricEvent, MetricMetadataDependency, StaticMetricMetadata,
7    },
8    property_set::{
9        PropertyDepsQueue, PropertySetDependency, PropertySetId, StringDepsQueue, record_properties,
10    },
11};
12use micromegas_transit::{StaticStringDependency, Utf8StaticStringDependency, prelude::*};
13use rustc_hash::FxHashSet;
14
15declare_queue_struct!(
16    struct MetricsMsgQueue<
17        IntegerMetricEvent,
18        FloatMetricEvent,
19        TaggedFloatMetricEvent,
20        TaggedIntegerMetricEvent,
21    > {}
22);
23
24declare_queue_struct!(
25    struct MetricsDepsQueue<
26        Utf8StaticStringDependency,
27        StaticStringDependency,
28        MetricMetadataDependency,
29        PropertySetDependency,
30    > {}
31);
32
33fn record_metric_event_dependencies(
34    metric_desc: &StaticMetricMetadata,
35    recorded_deps: &mut FxHashSet<u64>,
36    deps: &mut MetricsDepsQueue,
37) {
38    let metric_ptr = metric_desc as *const _ as u64;
39    if recorded_deps.insert(metric_ptr) {
40        let name = Utf8StaticStringDependency::from(metric_desc.name);
41        if recorded_deps.insert(name.ptr as u64) {
42            deps.push(name);
43        }
44        let unit = Utf8StaticStringDependency::from(metric_desc.unit);
45        if recorded_deps.insert(unit.ptr as u64) {
46            deps.push(unit);
47        }
48        let target = Utf8StaticStringDependency::from(metric_desc.target);
49        if recorded_deps.insert(target.ptr as u64) {
50            deps.push(target);
51        }
52        let file = Utf8StaticStringDependency::from(metric_desc.file);
53        if recorded_deps.insert(file.ptr as u64) {
54            deps.push(file);
55        }
56        deps.push(MetricMetadataDependency {
57            id: metric_ptr,
58            name: metric_desc.name.as_ptr(),
59            unit: metric_desc.unit.as_ptr(),
60            target: metric_desc.target.as_ptr(),
61            file: metric_desc.file.as_ptr(),
62            line: metric_desc.line,
63            lod: metric_desc.lod as u32,
64        });
65    }
66}
67
68impl ExtractDeps for MetricsMsgQueue {
69    type DepsQueue = MetricsDepsQueue;
70
71    fn extract(&self, dyn_deps: &DynDeps<Self::DepsQueue>) -> Self::DepsQueue {
72        let mut deps = MetricsDepsQueue::new(1024 * 1024);
73        let mut recorded_deps = FxHashSet::default();
74        let mut last_desc = 0u64;
75        let mut last_set = PropertySetId(0);
76        for x in self.iter() {
77            match x {
78                MetricsMsgQueueAny::IntegerMetricEvent(evt) => {
79                    let desc = evt.desc as *const _ as u64;
80                    if desc != last_desc {
81                        last_desc = desc;
82                        record_metric_event_dependencies(evt.desc, &mut recorded_deps, &mut deps);
83                    }
84                }
85                MetricsMsgQueueAny::FloatMetricEvent(evt) => {
86                    let desc = evt.desc as *const _ as u64;
87                    if desc != last_desc {
88                        last_desc = desc;
89                        record_metric_event_dependencies(evt.desc, &mut recorded_deps, &mut deps);
90                    }
91                }
92                MetricsMsgQueueAny::TaggedFloatMetricEvent(evt) => {
93                    let desc = evt.desc as *const _ as u64;
94                    if desc != last_desc {
95                        last_desc = desc;
96                        record_metric_event_dependencies(evt.desc, &mut recorded_deps, &mut deps);
97                    }
98                    if evt.properties != last_set {
99                        last_set = evt.properties;
100                        if let Some(set) = evt.properties.as_interned() {
101                            record_properties(set, &mut recorded_deps, &mut deps);
102                        }
103                    }
104                }
105                MetricsMsgQueueAny::TaggedIntegerMetricEvent(evt) => {
106                    let desc = evt.desc as *const _ as u64;
107                    if desc != last_desc {
108                        last_desc = desc;
109                        record_metric_event_dependencies(evt.desc, &mut recorded_deps, &mut deps);
110                    }
111                    if evt.properties != last_set {
112                        last_set = evt.properties;
113                        if let Some(set) = evt.properties.as_interned() {
114                            record_properties(set, &mut recorded_deps, &mut deps);
115                        }
116                    }
117                }
118            }
119        }
120        dyn_deps.record_static_refs(&mut recorded_deps, &mut deps);
121        deps.extend_from(dyn_deps.queue());
122        deps
123    }
124}
125
126impl StringDepsQueue for MetricsDepsQueue {
127    fn push_string(&mut self, dep: StaticStringDependency) {
128        self.push(dep);
129    }
130}
131
132impl PropertyDepsQueue for MetricsDepsQueue {
133    fn push_set(&mut self, dep: PropertySetDependency) {
134        self.push(dep);
135    }
136}
137
138pub type MetricsBlock = EventBlock<MetricsMsgQueue>;
139pub type MetricsStream = EventStream<MetricsBlock>;