1use std::{borrow, fmt, hash, ops};
2
3use bytestring::ByteString;
4
5mod symbol;
6mod variant;
7
8pub use self::symbol::{StaticSymbol, Symbol};
9pub use self::variant::{Variant, VariantMap, VecStringMap, VecSymbolMap};
10
11#[derive(Debug, PartialEq, Eq, Clone, Hash, Display)]
12pub enum Descriptor {
13 Ulong(u64),
14 Symbol(Symbol),
15}
16
17#[derive(Debug, PartialEq, Eq, Clone, Hash, From)]
18pub struct Multiple<T>(pub Vec<T>);
19
20impl<T> Multiple<T> {
21 pub fn len(&self) -> usize {
22 self.0.len()
23 }
24
25 pub fn is_empty(&self) -> bool {
26 self.0.is_empty()
27 }
28
29 pub fn iter(&self) -> ::std::slice::Iter<T> {
30 self.0.iter()
31 }
32}
33
34impl<T> Default for Multiple<T> {
35 fn default() -> Multiple<T> {
36 Multiple(Vec::new())
37 }
38}
39
40impl<T> ops::Deref for Multiple<T> {
41 type Target = Vec<T>;
42
43 fn deref(&self) -> &Self::Target {
44 &self.0
45 }
46}
47
48impl<T> ops::DerefMut for Multiple<T> {
49 fn deref_mut(&mut self) -> &mut Self::Target {
50 &mut self.0
51 }
52}
53
54#[derive(Debug, PartialEq, Eq, Clone, Hash)]
55pub struct List(pub Vec<Variant>);
56
57impl List {
58 pub fn len(&self) -> usize {
59 self.0.len()
60 }
61
62 pub fn is_empty(&self) -> bool {
63 self.0.is_empty()
64 }
65
66 pub fn iter(&self) -> ::std::slice::Iter<Variant> {
67 self.0.iter()
68 }
69}
70
71#[derive(Display, Clone, Eq, Ord, PartialOrd)]
72pub enum Str {
73 String(String),
74 ByteStr(ByteString),
75 Static(&'static str),
76}
77
78impl Str {
79 pub fn from_str(s: &str) -> Str {
80 Str::ByteStr(ByteString::from(s))
81 }
82
83 pub fn as_bytes(&self) -> &[u8] {
84 match self {
85 Str::String(s) => s.as_ref(),
86 Str::ByteStr(s) => s.as_ref(),
87 Str::Static(s) => s.as_bytes(),
88 }
89 }
90
91 pub fn as_str(&self) -> &str {
92 match self {
93 Str::String(s) => s.as_str(),
94 Str::ByteStr(s) => s.as_ref(),
95 Str::Static(s) => s,
96 }
97 }
98
99 pub fn to_bytes_str(&self) -> ByteString {
100 match self {
101 Str::String(s) => ByteString::from(s.as_str()),
102 Str::ByteStr(s) => s.clone(),
103 Str::Static(s) => ByteString::from_static(s),
104 }
105 }
106
107 pub fn len(&self) -> usize {
108 match self {
109 Str::String(s) => s.len(),
110 Str::ByteStr(s) => s.len(),
111 Str::Static(s) => s.len(),
112 }
113 }
114}
115
116impl From<&'static str> for Str {
117 fn from(s: &'static str) -> Str {
118 Str::Static(s)
119 }
120}
121
122impl From<ByteString> for Str {
123 fn from(s: ByteString) -> Str {
124 Str::ByteStr(s)
125 }
126}
127
128impl From<String> for Str {
129 fn from(s: String) -> Str {
130 Str::String(s)
131 }
132}
133
134impl hash::Hash for Str {
135 fn hash<H: hash::Hasher>(&self, state: &mut H) {
136 match self {
137 Str::String(s) => (&*s).hash(state),
138 Str::ByteStr(s) => (&*s).hash(state),
139 Str::Static(s) => s.hash(state),
140 }
141 }
142}
143
144impl borrow::Borrow<str> for Str {
145 fn borrow(&self) -> &str {
146 self.as_str()
147 }
148}
149
150impl PartialEq<Str> for Str {
151 fn eq(&self, other: &Str) -> bool {
152 match self {
153 Str::String(s) => match other {
154 Str::String(o) => s == o,
155 Str::ByteStr(o) => o == s.as_str(),
156 Str::Static(o) => s == *o,
157 },
158 Str::ByteStr(s) => match other {
159 Str::String(o) => s == o.as_str(),
160 Str::ByteStr(o) => s == o,
161 Str::Static(o) => s == *o,
162 },
163 Str::Static(s) => match other {
164 Str::String(o) => o == s,
165 Str::ByteStr(o) => o == *s,
166 Str::Static(o) => s == o,
167 },
168 }
169 }
170}
171
172impl PartialEq<str> for Str {
173 fn eq(&self, other: &str) -> bool {
174 match self {
175 Str::String(ref s) => s == other,
176 Str::ByteStr(ref s) => {
177 let t: &str = &*s;
179 t == other
180 }
181 Str::Static(s) => *s == other,
182 }
183 }
184}
185
186impl fmt::Debug for Str {
187 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
188 match self {
189 Str::String(s) => write!(f, "ST:\"{}\"", s),
190 Str::ByteStr(s) => write!(f, "B:\"{}\"", &*s),
191 Str::Static(s) => write!(f, "S:\"{}\"", s),
192 }
193 }
194}