tsproto_structs/
enums.rs

1use once_cell::sync::Lazy;
2use serde::Deserialize;
3
4pub const DATA_STR: &str =
5	include_str!(concat!(env!("CARGO_MANIFEST_DIR"), "/declarations/Enums.toml"));
6
7pub static DATA: Lazy<Enums> = Lazy::new(|| toml::from_str(DATA_STR).unwrap());
8
9#[derive(Deserialize, Debug)]
10#[serde(deny_unknown_fields)]
11pub struct Enums {
12	#[serde(rename = "enum")]
13	pub enums: Vec<Enum>,
14	#[serde(rename = "bitflag")]
15	pub bitflags: Vec<Enum>,
16}
17
18#[derive(Deserialize, Clone, Debug)]
19#[serde(deny_unknown_fields)]
20pub struct Enum {
21	pub name: String,
22	pub doc: Option<String>,
23	#[serde(rename = "type")]
24	pub use_type: Option<String>,
25	pub variants: Vec<Variant>,
26}
27
28#[derive(Deserialize, Clone, Debug)]
29#[serde(deny_unknown_fields)]
30pub struct Variant {
31	pub name: String,
32	pub doc: String,
33	pub value: Option<u64>,
34}
35
36impl Enum {
37	/// Computes the needed number of bits to store all possible variants.
38	pub fn bitwidth(&self) -> u32 {
39		let mut leading_zeros = 0;
40		let mut value: u64 = 0;
41		for v in &self.variants {
42			if let Some(v) = v.value {
43				leading_zeros = std::cmp::min(leading_zeros, value.leading_zeros());
44				value = v;
45			} else {
46				value += 1;
47			}
48		}
49		leading_zeros = std::cmp::min(leading_zeros, value.leading_zeros());
50		(64 - leading_zeros).next_power_of_two()
51	}
52}