binex/stream.rs
1//! BINEX Stream representation
2use crate::prelude::{ClosedSourceMeta, Message, Meta};
3
4/// [Message] [Provider]
5#[derive(Debug, Copy, Clone, PartialEq)]
6pub enum Provider {
7 /// JPL for internal needs or prototyping.
8 JPL,
9 /// IGS
10 IGS,
11 /// CU Boulder for internal needs or prototyping.
12 ColoradoUnivBoulder,
13 /// NRCan for internal needs or prototyping.
14 NRCan,
15 /// UCAR COSMIC <https://www.cosmic.ucar.edu>
16 UCAR,
17 /// GPS Solutions Inc.
18 GPSSolutions,
19 /// Astech Precision Products
20 Ashtech,
21 /// Topcon Positioning Systems
22 Topcon,
23}
24
25impl Provider {
26 /// Identify potential closed source [Provider]
27 /// from parsed MID (u32)
28 pub(crate) fn match_any(mid: u32) -> Option<Self> {
29 if (0x80..=0x87).contains(&mid) {
30 Some(Self::UCAR)
31 } else if (0x88..=0xa7).contains(&mid) {
32 Some(Self::Ashtech)
33 } else if (0xa8..=0xaf).contains(&mid) {
34 Some(Self::Topcon)
35 } else if (0xb0..=0xb3).contains(&mid) {
36 Some(Self::GPSSolutions)
37 } else if (0xb4..=0xb7).contains(&mid) {
38 Some(Self::NRCan)
39 } else if (0xb8..=0xbf).contains(&mid) {
40 Some(Self::JPL)
41 } else if (0xc0..=0xc3).contains(&mid) {
42 Some(Self::ColoradoUnivBoulder)
43 } else {
44 None
45 }
46 }
47}
48
49/// Closed source frame that we can encode but not interprate.
50/// This particular [StreamElement] can be either a part of a continuous serie or self sustainable.
51pub struct ClosedSourceElement<'a> {
52 /// [ClosedSourceMeta]
53 pub closed_meta: ClosedSourceMeta,
54 /// Raw data starting at first byte of undisclosed payload.
55 pub raw: &'a [u8],
56}
57
58impl<'a> ClosedSourceElement<'a> {
59 /// Interprate this [ClosedSourceElement] using custom undisclosed method.
60 pub fn interprate(&self, f: &dyn Fn(&[u8])) {
61 f(&self.raw[..self.closed_meta.size])
62 }
63
64 /// Returns reference to raw data "as is", since interpration is not possible
65 pub fn raw(&self) -> &'a [u8] {
66 &self.raw[..self.closed_meta.size]
67 }
68}
69
70/// [StreamElement] represents one element of a continuous BINEX stream.
71pub enum StreamElement<'a> {
72 /// Open Source [Message] we can fully decode & interprate
73 OpenSource(Message),
74 /// One non disclosed [ClosedSourceElement] that may be part of a continuous serie of elements.
75 /// Each chunk of the serie is internally limited to 4096 bytes.
76 /// While we can encode and decode this serie, we cannot interprate it.
77 ClosedSource(ClosedSourceElement<'a>),
78}
79
80impl<'a> From<Message> for StreamElement<'a> {
81 fn from(msg: Message) -> Self {
82 Self::OpenSource(msg)
83 }
84}
85
86impl<'a> StreamElement<'a> {
87 /// Creates a new open source [Message] ready to be encoded
88 pub fn new_open_source(msg: Message) -> Self {
89 Self::OpenSource(msg)
90 }
91
92 /// Creates a new self sustained closed source [StreamElement] provided by desired [Provider].
93 /// ## Inputs
94 /// - meta: [Meta] data of this prototype
95 /// - provider: specific [Provider]
96 /// - mid: message ID
97 /// - mlen: total payload length (bytes)
98 /// - raw: chunk we can encode, decode but not fully interprate
99 /// - size: size of this chunk
100 pub fn new_prototype(
101 open_meta: Meta,
102 provider: Provider,
103 mid: u32,
104 mlen: usize,
105 raw: &'a [u8],
106 size: usize,
107 ) -> Self {
108 Self::ClosedSource(ClosedSourceElement {
109 raw,
110 closed_meta: ClosedSourceMeta {
111 mid,
112 mlen,
113 open_meta,
114 provider,
115 offset: 0,
116 size,
117 },
118 })
119 }
120
121 /// Add one closed source [StreamElement]s provided by desired [Provider::JPL].
122 /// While we can encode this into a BINEX stream, only this organization can fully interprate the resulting stream.
123 /// ## Inputs
124 /// - meta: [Meta] of this message prototype
125 /// - mid: message ID
126 /// - mlen: total payload length (bytes)
127 /// - raw: content we can encode, decode but not interprate
128 /// - total: total size of the closed source Message (bytewise).
129 /// It's either equal to [Meta::mlen] if this prototype if self sustainable,
130 /// or larger, in case this prototype is only one element of a serie.
131 pub fn jpl_prototype(meta: Meta, mid: u32, mlen: usize, raw: &'a [u8], size: usize) -> Self {
132 Self::new_prototype(meta, Provider::JPL, mid, mlen, raw, size)
133 }
134
135 /// Add one closed source [StreamElement]s provided by desired [Provider::JPL].
136 /// While we can encode this into a BINEX stream, only this organization can fully interprate the resulting stream.
137 /// ## Inputs
138 /// - meta: [Meta] of this message prototype
139 /// - raw: content we can encode, decode but not interprate
140 /// - total: total size of the closed source Message (bytewise).
141 /// It's either equal to [Meta::mlen] if this prototype if self sustainable,
142 /// or larger, in case this prototype is only one element of a serie.
143 pub fn igs_prototype(meta: Meta, mid: u32, mlen: usize, raw: &'a [u8], size: usize) -> Self {
144 Self::new_prototype(meta, Provider::IGS, mid, mlen, raw, size)
145 }
146
147 /// Add one closed source [StreamElement]s provided by desired [Provider::ColoradoUnivBoulder].
148 /// While we can encode this into a BINEX stream, only this organization can fully interprate the resulting stream.
149 /// ## Inputs
150 /// - meta: [Meta] of this message prototype
151 /// - mid: message ID
152 /// - mlen: total payload length (bytes)
153 /// - raw: content we can encode, decode but not interprate
154 /// - total: total size of the closed source Message (bytewise).
155 /// It's either equal to [Meta::mlen] if this prototype if self sustainable,
156 /// or larger, in case this prototype is only one element of a serie.
157 pub fn cuboulder_prototype(
158 meta: Meta,
159 mid: u32,
160 mlen: usize,
161 raw: &'a [u8],
162 size: usize,
163 ) -> Self {
164 Self::new_prototype(meta, Provider::ColoradoUnivBoulder, mid, mlen, raw, size)
165 }
166
167 /// Add one closed source [StreamElement]s provided by desired [Provider::NRCan].
168 /// While we can encode this into a BINEX stream, only this organization can fully interprate the resulting stream.
169 /// ## Inputs
170 /// - meta: [Meta] of this message prototype
171 /// - mid: message ID
172 /// - mlen: total payload length (bytes)
173 /// - raw: content we can encode, decode but not interprate
174 /// - total: total size of the closed source Message (bytewise).
175 /// It's either equal to [Meta::mlen] if this prototype if self sustainable,
176 /// or larger, in case this prototype is only one element of a serie.
177 pub fn nrcan_prototype(meta: Meta, mid: u32, mlen: usize, raw: &'a [u8], size: usize) -> Self {
178 Self::new_prototype(meta, Provider::NRCan, mid, mlen, raw, size)
179 }
180
181 /// Add one closed source [StreamElement]s provided by desired [Provider::UCAR].
182 /// While we can encode this into a BINEX stream, only this organization can fully interprate the resulting stream.
183 /// ## Inputs
184 /// - meta: [Meta] of this message prototype
185 /// - mid: message ID
186 /// - mlen: total payload length (bytes)
187 /// - raw: content we can encode, decode but not interprate
188 /// - total: total size of the closed source Message (bytewise).
189 /// It's either equal to [Meta::mlen] if this prototype if self sustainable,
190 /// or larger, in case this prototype is only one element of a serie.
191 pub fn ucar_prototype(meta: Meta, mid: u32, mlen: usize, raw: &'a [u8], size: usize) -> Self {
192 Self::new_prototype(meta, Provider::UCAR, mid, mlen, raw, size)
193 }
194}