1use crate::codec::primitive_type_codec::PrimitiveTypeCodec;
2use crate::codec::signal_codec::SignalCodec;
3use crate::token::TryFromPrimitiveValueIntError::InvalidPrimitiveType;
4use std::ascii;
5use std::borrow::Cow;
6use std::fmt::{Debug, Display, Formatter, Write};
7use std::num::TryFromIntError;
8use thiserror::Error;
9
10pub struct Token {
12 pub i: usize,
13 pub signal: Signal,
14 pub name: String,
15 pub referenced_name: String,
16 pub description: String,
17 pub id: i32,
19 pub version: i32,
20 pub deprecated: Option<i32>,
21 pub encoded_length: i32,
22 pub offset: i32,
23 pub component_token_count: i32,
24 pub encoding: Encoding,
25}
26
27impl Debug for Token {
28 fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
29 f.debug_struct("Token")
30 .field("i", &self.i)
31 .field("signal", &self.signal)
32 .field("name", &self.name)
33 .field("enc_length", &self.encoded_length)
34 .field("offset", &self.offset)
35 .field("comp_tok_count", &self.component_token_count)
36 .field("e.primitive_type", &self.encoding.primitive_type)
37 .field("e.const_value", &self.encoding.const_value)
38 .finish()
39 }
40}
41
42impl Token {
43 pub fn array_length(&self) -> usize {
44 if self.encoding.primitive_type == PrimitiveType::None || self.encoded_length == 0 {
45 0
46 } else {
47 self.encoded_length as usize / self.encoding.primitive_type.size()
48 }
49 }
50}
51
52#[derive(Debug)]
53pub struct Encoding {
54 pub presence: Presence,
55 pub primitive_type: PrimitiveType,
56 pub byte_order: ByteOrder,
57 pub const_value: PrimitiveValue,
58 pub min_value: PrimitiveValue,
59 pub max_value: PrimitiveValue,
60 pub null_value: PrimitiveValue,
61 pub character_encoding: String,
62 pub epoch: String,
63 pub time_unit: String,
64 pub semantic_type: String,
65}
66
67impl Encoding {
68 pub const fn applicable_null_value(&self) -> &PrimitiveValue {
69 match &self.null_value {
70 PrimitiveValue::None => self.primitive_type.null_value(),
71 _ => &self.null_value,
72 }
73 }
74}
75
76#[derive(Debug, Copy, Clone, Eq, PartialEq)]
77pub enum PrimitiveType {
78 None,
79 Char,
80 Int8,
81 Int16,
82 Int32,
83 Int64,
84 UInt8,
85 UInt16,
86 UInt32,
87 UInt64,
88 Float,
89 Double,
90}
91
92impl PrimitiveType {
93 pub const fn null_value(&self) -> &PrimitiveValue {
94 match self {
95 PrimitiveType::None => &PrimitiveValue::None,
96 PrimitiveType::Char => &PrimitiveValue::Char(NULL_VALUE_CHAR),
97 PrimitiveType::Int8 => &PrimitiveValue::Int8(NULL_VALUE_INT8),
98 PrimitiveType::Int16 => &PrimitiveValue::Int16(NULL_VALUE_INT16),
99 PrimitiveType::Int32 => &PrimitiveValue::Int32(NULL_VALUE_INT32),
100 PrimitiveType::Int64 => &PrimitiveValue::Int64(NULL_VALUE_INT64),
101 PrimitiveType::UInt8 => &PrimitiveValue::UInt8(NULL_VALUE_UINT8),
102 PrimitiveType::UInt16 => &PrimitiveValue::UInt16(NULL_VALUE_UINT16),
103 PrimitiveType::UInt32 => &PrimitiveValue::UInt32(NULL_VALUE_UINT32),
104 PrimitiveType::UInt64 => &PrimitiveValue::UInt64(NULL_VALUE_UINT64),
105 PrimitiveType::Float => &PrimitiveValue::Float(NULL_VALUE_FLOAT),
106 PrimitiveType::Double => &PrimitiveValue::Double(NULL_VALUE_DOUBLE),
107 }
108 }
109
110 pub const fn max_value(&self) -> &PrimitiveValue {
111 match self {
112 PrimitiveType::None => &const { PrimitiveValue::None },
113 PrimitiveType::Char => &const { PrimitiveValue::Char(MAX_VALUE_CHAR) },
114 PrimitiveType::Int8 => &const { PrimitiveValue::Int8(MAX_VALUE_INT8) },
115 PrimitiveType::Int16 => &const { PrimitiveValue::Int16(MAX_VALUE_INT16) },
116 PrimitiveType::Int32 => &const { PrimitiveValue::Int32(MAX_VALUE_INT32) },
117 PrimitiveType::Int64 => &const { PrimitiveValue::Int64(MAX_VALUE_INT64) },
118 PrimitiveType::UInt8 => &const { PrimitiveValue::UInt8(MAX_VALUE_UINT8) },
119 PrimitiveType::UInt16 => &const { PrimitiveValue::UInt16(MAX_VALUE_UINT16) },
120 PrimitiveType::UInt32 => &const { PrimitiveValue::UInt32(MAX_VALUE_UINT32) },
121 PrimitiveType::UInt64 => &const { PrimitiveValue::UInt64(MAX_VALUE_UINT64) },
122 PrimitiveType::Float => &const { PrimitiveValue::Float(MAX_VALUE_FLOAT) },
123 PrimitiveType::Double => &const { PrimitiveValue::Double(MAX_VALUE_DOUBLE) },
124 }
125 }
126
127 pub const fn min_value(&self) -> PrimitiveValue {
128 match self {
129 PrimitiveType::None => PrimitiveValue::None,
130 PrimitiveType::Char => PrimitiveValue::Char(MIN_VALUE_CHAR),
131 PrimitiveType::Int8 => PrimitiveValue::Int8(MIN_VALUE_INT8),
132 PrimitiveType::Int16 => PrimitiveValue::Int16(MIN_VALUE_INT16),
133 PrimitiveType::Int32 => PrimitiveValue::Int32(MIN_VALUE_INT32),
134 PrimitiveType::Int64 => PrimitiveValue::Int64(MIN_VALUE_INT64),
135 PrimitiveType::UInt8 => PrimitiveValue::UInt8(MIN_VALUE_UINT8),
136 PrimitiveType::UInt16 => PrimitiveValue::UInt16(MIN_VALUE_UINT16),
137 PrimitiveType::UInt32 => PrimitiveValue::UInt32(MIN_VALUE_UINT32),
138 PrimitiveType::UInt64 => PrimitiveValue::UInt64(MIN_VALUE_UINT64),
139 PrimitiveType::Float => PrimitiveValue::Float(MIN_VALUE_FLOAT),
140 PrimitiveType::Double => PrimitiveValue::Double(MIN_VALUE_DOUBLE),
141 }
142 }
143
144 pub const fn name(&self) -> &'static str {
145 match self {
146 PrimitiveType::None => "null",
147 PrimitiveType::Char => "char",
148 PrimitiveType::Int8 => "int8",
149 PrimitiveType::Int16 => "int16",
150 PrimitiveType::Int32 => "int32",
151 PrimitiveType::Int64 => "int64",
152 PrimitiveType::UInt8 => "uint8",
153 PrimitiveType::UInt16 => "uint16",
154 PrimitiveType::UInt32 => "uint32",
155 PrimitiveType::UInt64 => "uint64",
156 PrimitiveType::Float => "float",
157 PrimitiveType::Double => "double",
158 }
159 }
160
161 pub const fn size(&self) -> usize {
162 match self {
163 PrimitiveType::None => size_of::<()>(),
164 PrimitiveType::Char => size_of::<u8>(),
165 PrimitiveType::Int8 => size_of::<i8>(),
166 PrimitiveType::Int16 => size_of::<i16>(),
167 PrimitiveType::Int32 => size_of::<i32>(),
168 PrimitiveType::Int64 => size_of::<i64>(),
169 PrimitiveType::UInt8 => size_of::<i8>(),
170 PrimitiveType::UInt16 => size_of::<u16>(),
171 PrimitiveType::UInt32 => size_of::<u32>(),
172 PrimitiveType::UInt64 => size_of::<u64>(),
173 PrimitiveType::Float => size_of::<f32>(),
174 PrimitiveType::Double => size_of::<f64>(),
175 }
176 }
177}
178
179impl Display for PrimitiveType {
180 fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
181 write!(f, "{}", self.name())
182 }
183}
184
185#[derive(Debug, Copy, Clone, PartialEq)]
186enum Representation {
187 Integer(u64),
188 Float(f64),
189}
190
191#[derive(Debug, PartialEq)]
192pub struct PrimitiveValue2 {
193 representation: Representation,
194 primitive_type: PrimitiveType,
195}
196
197#[derive(Debug, PartialEq)]
198pub enum PrimitiveValue {
199 None,
200 Char(u8),
201 Int8(i8),
202 Int16(i16),
203 Int32(i32),
204 Int64(i64),
205 UInt8(u8),
206 UInt16(u16),
207 UInt32(u32),
208 UInt64(u64),
209 Float(f32),
210 Double(f64),
211 ByteArray(Vec<u8>),
212}
213
214impl PrimitiveValue {
215 pub fn new(primitive_type: PrimitiveType, value: &[u8]) -> Self {
216 if value.is_empty() {
217 return PrimitiveValue::None;
218 }
219 match primitive_type {
220 PrimitiveType::None => Self::None,
222 PrimitiveType::Char => {
223 if value.len() == 1 {
224 Self::Char(value[0])
225 } else {
226 Self::ByteArray(value.to_vec())
227 }
228 }
229 PrimitiveType::Int8 => Self::Int8(i8::from_le_bytes(value.try_into().unwrap())),
230 PrimitiveType::Int16 => Self::Int16(i16::from_le_bytes(value.try_into().unwrap())),
231 PrimitiveType::Int32 => Self::Int32(i32::from_le_bytes(value.try_into().unwrap())),
232 PrimitiveType::Int64 => Self::Int64(i64::from_le_bytes(value.try_into().unwrap())),
233 PrimitiveType::UInt8 => Self::UInt8(u8::from_le_bytes(value.try_into().unwrap())),
234 PrimitiveType::UInt16 => Self::UInt16(u16::from_le_bytes(value.try_into().unwrap())),
235 PrimitiveType::UInt32 => Self::UInt32(u32::from_le_bytes(value.try_into().unwrap())),
236 PrimitiveType::UInt64 => Self::UInt64(u64::from_le_bytes(value.try_into().unwrap())),
237 PrimitiveType::Float => Self::Float(f32::from_le_bytes(value.try_into().unwrap())),
238 PrimitiveType::Double => Self::Double(f64::from_le_bytes(value.try_into().unwrap())),
239 }
240 }
241
242 pub fn is_none(&self) -> bool {
243 matches!(self, PrimitiveValue::None)
244 }
245
246 pub fn primitive_type(&self) -> PrimitiveType {
247 match self {
248 PrimitiveValue::None => PrimitiveType::None,
249 PrimitiveValue::Char(_) => PrimitiveType::Char,
250 PrimitiveValue::Int8(_) => PrimitiveType::Int8,
251 PrimitiveValue::Int16(_) => PrimitiveType::Int16,
252 PrimitiveValue::Int32(_) => PrimitiveType::Int32,
253 PrimitiveValue::Int64(_) => PrimitiveType::Int64,
254 PrimitiveValue::UInt8(_) => PrimitiveType::UInt8,
255 PrimitiveValue::UInt16(_) => PrimitiveType::UInt16,
256 PrimitiveValue::UInt32(_) => PrimitiveType::UInt32,
257 PrimitiveValue::UInt64(_) => PrimitiveType::UInt64,
258 PrimitiveValue::Float(_) => PrimitiveType::Float,
259 PrimitiveValue::Double(_) => PrimitiveType::Double,
260 PrimitiveValue::ByteArray(_) => todo!(),
261 }
262 }
263
264 pub fn to_string(&self) -> Cow<str> {
265 match self {
266 PrimitiveValue::None => "".into(),
267 PrimitiveValue::Char(val) => val.to_string().into(),
268 PrimitiveValue::Int8(val) => val.to_string().into(),
269 PrimitiveValue::Int16(val) => val.to_string().into(),
270 PrimitiveValue::Int32(val) => val.to_string().into(),
271 PrimitiveValue::Int64(val) => val.to_string().into(),
272 PrimitiveValue::UInt8(val) => val.to_string().into(),
273 PrimitiveValue::UInt16(val) => val.to_string().into(),
274 PrimitiveValue::UInt32(val) => val.to_string().into(),
275 PrimitiveValue::UInt64(val) => val.to_string().into(),
276 PrimitiveValue::Float(val) => val.to_string().into(),
277 PrimitiveValue::Double(val) => val.to_string().into(),
278 PrimitiveValue::ByteArray(val) => String::from_utf8_lossy(
279 &val.iter()
280 .cloned()
281 .flat_map(ascii::escape_default)
282 .collect::<Vec<u8>>(),
283 )
284 .to_string()
285 .into(),
286 }
287 }
288}
289
290#[derive(Error, Debug)]
291pub enum TryFromPrimitiveValueIntError {
292 #[error("primitive value of type {0} can not be converted to u64")]
293 InvalidPrimitiveType(PrimitiveType),
294
295 #[error(transparent)]
296 InvalidPrimitiveValue(TryFromIntError),
297}
298
299impl TryFrom<PrimitiveValue> for u64 {
300 type Error = TryFromPrimitiveValueIntError;
301
302 fn try_from(value: PrimitiveValue) -> Result<Self, Self::Error> {
303 (&value).try_into()
304 }
305}
306
307impl TryFrom<&PrimitiveValue> for u64 {
308 type Error = TryFromPrimitiveValueIntError;
309
310 fn try_from(value: &PrimitiveValue) -> Result<Self, Self::Error> {
311 match value {
312 PrimitiveValue::Char(val) => Ok((*val).into()),
313 PrimitiveValue::Int8(val) => (*val)
314 .try_into()
315 .map_err(TryFromPrimitiveValueIntError::InvalidPrimitiveValue),
316 PrimitiveValue::Int16(val) => (*val)
317 .try_into()
318 .map_err(TryFromPrimitiveValueIntError::InvalidPrimitiveValue),
319 PrimitiveValue::Int32(val) => (*val)
320 .try_into()
321 .map_err(TryFromPrimitiveValueIntError::InvalidPrimitiveValue),
322 PrimitiveValue::Int64(val) => (*val)
323 .try_into()
324 .map_err(TryFromPrimitiveValueIntError::InvalidPrimitiveValue),
325 PrimitiveValue::UInt8(val) => Ok((*val).into()),
326 PrimitiveValue::UInt16(val) => Ok((*val).into()),
327 PrimitiveValue::UInt32(val) => Ok((*val).into()),
328 PrimitiveValue::UInt64(val) => Ok((*val).into()),
329 PrimitiveValue::None
330 | PrimitiveValue::Float(_)
331 | PrimitiveValue::Double(_)
332 | PrimitiveValue::ByteArray(_) => Err(InvalidPrimitiveType(value.primitive_type())),
333 }
334 }
335}
336
337impl Display for PrimitiveValue {
338 fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
339 match self {
340 PrimitiveValue::None => write!(f, "NULL_VAL"),
341 PrimitiveValue::Char(val) => write!(f, "'{}'", *val as char),
342 PrimitiveValue::Int8(val) => write!(f, "{val}"),
343 PrimitiveValue::Int16(val) => write!(f, "{val}"),
344 PrimitiveValue::Int32(val) => write!(f, "{val}"),
345 PrimitiveValue::Int64(val) => write!(f, "{val}"),
346 PrimitiveValue::UInt8(val) => write!(f, "{val}"),
347 PrimitiveValue::UInt16(val) => write!(f, "{val}"),
348 PrimitiveValue::UInt32(val) => write!(f, "{val}"),
349 PrimitiveValue::UInt64(val) => write!(f, "{val}"),
350 PrimitiveValue::Float(val) => write!(f, "{val}"),
351 PrimitiveValue::Double(val) => write!(f, "{val}"),
352 PrimitiveValue::ByteArray(val) => val
353 .iter()
354 .try_for_each(|b| write!(f, "{}", (*b as char).escape_default())),
355 }
356 }
357}
358
359pub const MIN_VALUE_CHAR: u8 = 0x20;
361
362pub const MAX_VALUE_CHAR: u8 = 0x7E;
364
365pub const NULL_VALUE_CHAR: u8 = 0;
367
368pub const MIN_VALUE_INT8: i8 = -127;
370
371pub const MAX_VALUE_INT8: i8 = 127;
373
374pub const NULL_VALUE_INT8: i8 = -128;
376
377pub const MIN_VALUE_UINT8: u8 = 0;
379
380pub const MAX_VALUE_UINT8: u8 = 254;
382
383pub const NULL_VALUE_UINT8: u8 = 255;
385
386pub const MIN_VALUE_INT16: i16 = -32767;
388
389pub const MAX_VALUE_INT16: i16 = 32767;
391
392pub const NULL_VALUE_INT16: i16 = -32768;
394
395pub const MIN_VALUE_UINT16: u16 = 0;
397
398pub const MAX_VALUE_UINT16: u16 = 65534;
400
401pub const NULL_VALUE_UINT16: u16 = 65535;
403
404pub const MIN_VALUE_INT32: i32 = -2147483647;
406
407pub const MAX_VALUE_INT32: i32 = 2147483647;
409
410pub const NULL_VALUE_INT32: i32 = -2147483648;
412
413pub const MIN_VALUE_UINT32: u32 = 0;
415
416pub const MAX_VALUE_UINT32: u32 = 0xFFFF_FFFF - 1;
418
419pub const NULL_VALUE_UINT32: u32 = 0xFFFF_FFFF;
421
422pub const MIN_VALUE_INT64: i64 = i64::MIN + 1; pub const MAX_VALUE_INT64: i64 = i64::MAX; pub const NULL_VALUE_INT64: i64 = i64::MIN; pub const MIN_VALUE_UINT64: u64 = 0;
433
434pub const MAX_VALUE_UINT64: u64 = 18446744073709551614; pub const NULL_VALUE_UINT64: u64 = 18446744073709551615; pub const MIN_VALUE_FLOAT: f32 = -f32::MAX;
442
443pub const MAX_VALUE_FLOAT: f32 = f32::MAX;
445
446pub const NULL_VALUE_FLOAT: f32 = f32::NAN;
448
449pub const MIN_VALUE_DOUBLE: f64 = -f64::MAX;
451
452pub const MAX_VALUE_DOUBLE: f64 = f64::MAX;
454
455pub const NULL_VALUE_DOUBLE: f64 = f64::NAN;
457
458#[derive(Debug, Eq, PartialEq, Copy, Clone)]
459pub enum ByteOrder {
460 LittleEndian,
461 BigEndian,
462}
463
464#[derive(Debug, Eq, PartialEq, Copy, Clone)]
465pub enum Presence {
466 Required,
467 Optional,
468 Constant,
469}
470
471#[derive(Debug, Eq, PartialEq, Copy, Clone)]
472pub enum Signal {
473 BeginMessage,
475
476 EndMessage,
478
479 BeginComposite,
481
482 EndComposite,
484
485 BeginField,
487
488 EndField,
490
491 BeginGroup,
493
494 EndGroup,
496
497 BeginEnum,
499
500 ValidValue,
502
503 EndEnum,
505
506 BeginSet,
508
509 Choice,
511
512 EndSet,
514
515 BeginVarData,
517
518 EndVarData,
520
521 Encoding,
523}
524
525impl Signal {
526 pub const fn flip(&self) -> Option<Self> {
527 match self {
528 Signal::BeginMessage => Some(Signal::EndMessage),
529 Signal::BeginComposite => Some(Signal::EndComposite),
530 Signal::BeginField => Some(Signal::EndField),
531 Signal::BeginGroup => Some(Signal::EndGroup),
532 Signal::BeginEnum => Some(Signal::EndEnum),
533 Signal::BeginSet => Some(Signal::EndSet),
534 Signal::BeginVarData => Some(Signal::EndVarData),
535 Signal::EndMessage => Some(Signal::BeginMessage),
536 Signal::EndComposite => Some(Signal::BeginComposite),
537 Signal::EndField => Some(Signal::BeginField),
538 Signal::EndGroup => Some(Signal::BeginGroup),
539 Signal::EndEnum => Some(Signal::BeginEnum),
540 Signal::EndSet => Some(Signal::BeginSet),
541 Signal::EndVarData => Some(Signal::BeginVarData),
542 Signal::ValidValue | Signal::Choice | Signal::Encoding => None,
543 }
544 }
545}
546
547impl From<SignalCodec> for Signal {
548 fn from(value: SignalCodec) -> Self {
549 match value {
550 SignalCodec::BEGIN_MESSAGE => Signal::BeginMessage,
551 SignalCodec::END_MESSAGE => Signal::EndMessage,
552 SignalCodec::BEGIN_COMPOSITE => Signal::BeginComposite,
553 SignalCodec::END_COMPOSITE => Signal::EndComposite,
554 SignalCodec::BEGIN_FIELD => Signal::BeginField,
555 SignalCodec::END_FIELD => Signal::EndField,
556 SignalCodec::BEGIN_GROUP => Signal::BeginGroup,
557 SignalCodec::END_GROUP => Signal::EndGroup,
558 SignalCodec::BEGIN_ENUM => Signal::BeginEnum,
559 SignalCodec::VALID_VALUE => Signal::ValidValue,
560 SignalCodec::END_ENUM => Signal::EndEnum,
561 SignalCodec::BEGIN_SET => Signal::BeginSet,
562 SignalCodec::CHOICE => Signal::Choice,
563 SignalCodec::END_SET => Signal::EndSet,
564 SignalCodec::BEGIN_VAR_DATA => Signal::BeginVarData,
565 SignalCodec::END_VAR_DATA => Signal::EndVarData,
566 SignalCodec::ENCODING => Signal::Encoding,
567 SignalCodec::NullVal => panic!("null signal"), }
569 }
570}
571
572impl From<PrimitiveTypeCodec> for PrimitiveType {
573 fn from(value: PrimitiveTypeCodec) -> Self {
574 match value {
575 PrimitiveTypeCodec::NONE => PrimitiveType::None,
576 PrimitiveTypeCodec::CHAR => PrimitiveType::Char,
577 PrimitiveTypeCodec::INT8 => PrimitiveType::Int8,
578 PrimitiveTypeCodec::INT16 => PrimitiveType::Int16,
579 PrimitiveTypeCodec::INT32 => PrimitiveType::Int32,
580 PrimitiveTypeCodec::INT64 => PrimitiveType::Int64,
581 PrimitiveTypeCodec::UINT8 => PrimitiveType::UInt8,
582 PrimitiveTypeCodec::UINT16 => PrimitiveType::UInt16,
583 PrimitiveTypeCodec::UINT32 => PrimitiveType::UInt32,
584 PrimitiveTypeCodec::UINT64 => PrimitiveType::UInt64,
585 PrimitiveTypeCodec::FLOAT => PrimitiveType::Float,
586 PrimitiveTypeCodec::DOUBLE => PrimitiveType::Double,
587 PrimitiveTypeCodec::NullVal => panic!("null primitive type"), }
589 }
590}