1use std::cmp::Ordering;
4use std::collections::BTreeMap;
5use std::io::Write;
6use std::iter::FromIterator;
7use std::ops::Deref;
8use std::sync::Arc;
9
10use byteorder::{BigEndian, ByteOrder};
11use libipld_core::cid::Cid;
12use libipld_core::codec::Encode;
13use libipld_core::error::Result;
14use libipld_core::ipld::Ipld;
15
16use crate::cbor::{MajorKind, FALSE, TRUE};
17use crate::error::NumberOutOfRange;
18use crate::DagCborCodec as DagCbor;
19
20pub fn write_null<W: Write>(w: &mut W) -> Result<()> {
22 w.write_all(&[0xf6])?;
23 Ok(())
24}
25
26pub fn write_u8<W: Write>(w: &mut W, major: MajorKind, value: u8) -> Result<()> {
28 let major = major as u8;
29 if value <= 0x17 {
30 let buf = [major << 5 | value];
31 w.write_all(&buf)?;
32 } else {
33 let buf = [major << 5 | 24, value];
34 w.write_all(&buf)?;
35 }
36 Ok(())
37}
38
39pub fn write_u16<W: Write>(w: &mut W, major: MajorKind, value: u16) -> Result<()> {
41 if value <= u16::from(u8::max_value()) {
42 write_u8(w, major, value as u8)?;
43 } else {
44 let mut buf = [(major as u8) << 5 | 25, 0, 0];
45 BigEndian::write_u16(&mut buf[1..], value);
46 w.write_all(&buf)?;
47 }
48 Ok(())
49}
50
51pub fn write_u32<W: Write>(w: &mut W, major: MajorKind, value: u32) -> Result<()> {
53 if value <= u32::from(u16::max_value()) {
54 write_u16(w, major, value as u16)?;
55 } else {
56 let mut buf = [(major as u8) << 5 | 26, 0, 0, 0, 0];
57 BigEndian::write_u32(&mut buf[1..], value);
58 w.write_all(&buf)?;
59 }
60 Ok(())
61}
62
63pub fn write_u64<W: Write>(w: &mut W, major: MajorKind, value: u64) -> Result<()> {
65 if value <= u64::from(u32::max_value()) {
66 write_u32(w, major, value as u32)?;
67 } else {
68 let mut buf = [(major as u8) << 5 | 27, 0, 0, 0, 0, 0, 0, 0, 0];
69 BigEndian::write_u64(&mut buf[1..], value);
70 w.write_all(&buf)?;
71 }
72 Ok(())
73}
74
75pub fn write_tag<W: Write>(w: &mut W, tag: u64) -> Result<()> {
77 write_u64(w, MajorKind::Tag, tag)
78}
79
80impl Encode<DagCbor> for bool {
81 fn encode<W: Write>(&self, _: DagCbor, w: &mut W) -> Result<()> {
82 let buf = if *self { [TRUE.into()] } else { [FALSE.into()] };
83 w.write_all(&buf)?;
84 Ok(())
85 }
86}
87
88impl Encode<DagCbor> for u8 {
89 fn encode<W: Write>(&self, _: DagCbor, w: &mut W) -> Result<()> {
90 write_u8(w, MajorKind::UnsignedInt, *self)
91 }
92}
93
94impl Encode<DagCbor> for u16 {
95 fn encode<W: Write>(&self, _: DagCbor, w: &mut W) -> Result<()> {
96 write_u16(w, MajorKind::UnsignedInt, *self)
97 }
98}
99
100impl Encode<DagCbor> for u32 {
101 fn encode<W: Write>(&self, _: DagCbor, w: &mut W) -> Result<()> {
102 write_u32(w, MajorKind::UnsignedInt, *self)
103 }
104}
105
106impl Encode<DagCbor> for u64 {
107 fn encode<W: Write>(&self, _: DagCbor, w: &mut W) -> Result<()> {
108 write_u64(w, MajorKind::UnsignedInt, *self)
109 }
110}
111
112impl Encode<DagCbor> for i8 {
113 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
114 if self.is_negative() {
115 write_u8(w, MajorKind::NegativeInt, -(*self + 1) as u8)
116 } else {
117 (*self as u8).encode(c, w)
118 }
119 }
120}
121
122impl Encode<DagCbor> for i16 {
123 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
124 if self.is_negative() {
125 write_u16(w, MajorKind::NegativeInt, -(*self + 1) as u16)
126 } else {
127 (*self as u16).encode(c, w)
128 }
129 }
130}
131
132impl Encode<DagCbor> for i32 {
133 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
134 if self.is_negative() {
135 write_u32(w, MajorKind::NegativeInt, -(*self + 1) as u32)
136 } else {
137 (*self as u32).encode(c, w)
138 }
139 }
140}
141
142impl Encode<DagCbor> for i64 {
143 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
144 if self.is_negative() {
145 write_u64(w, MajorKind::NegativeInt, -(*self + 1) as u64)
146 } else {
147 (*self as u64).encode(c, w)
148 }
149 }
150}
151
152impl Encode<DagCbor> for f32 {
153 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
154 f64::from(*self).encode(c, w)
156 }
157}
158
159impl Encode<DagCbor> for f64 {
160 fn encode<W: Write>(&self, _: DagCbor, w: &mut W) -> Result<()> {
161 if !self.is_finite() {
163 return Err(NumberOutOfRange::new::<f64>().into());
164 }
165 let mut buf = [0xfb, 0, 0, 0, 0, 0, 0, 0, 0];
166 BigEndian::write_f64(&mut buf[1..], *self);
167 w.write_all(&buf)?;
168 Ok(())
169 }
170}
171
172impl Encode<DagCbor> for [u8] {
173 fn encode<W: Write>(&self, _: DagCbor, w: &mut W) -> Result<()> {
174 write_u64(w, MajorKind::ByteString, self.len() as u64)?;
175 w.write_all(self)?;
176 Ok(())
177 }
178}
179
180impl Encode<DagCbor> for Box<[u8]> {
181 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
182 self[..].encode(c, w)
183 }
184}
185
186impl Encode<DagCbor> for str {
187 fn encode<W: Write>(&self, _: DagCbor, w: &mut W) -> Result<()> {
188 write_u64(w, MajorKind::TextString, self.len() as u64)?;
189 w.write_all(self.as_bytes())?;
190 Ok(())
191 }
192}
193
194impl Encode<DagCbor> for String {
195 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
196 self.as_str().encode(c, w)
197 }
198}
199
200impl Encode<DagCbor> for i128 {
201 fn encode<W: Write>(&self, _: DagCbor, w: &mut W) -> Result<()> {
202 if *self < 0 {
203 if -(*self + 1) > u64::max_value() as i128 {
204 return Err(NumberOutOfRange::new::<i128>().into());
205 }
206 write_u64(w, MajorKind::NegativeInt, -(*self + 1) as u64)?;
207 } else {
208 if *self > u64::max_value() as i128 {
209 return Err(NumberOutOfRange::new::<i128>().into());
210 }
211 write_u64(w, MajorKind::UnsignedInt, *self as u64)?;
212 }
213 Ok(())
214 }
215}
216
217impl Encode<DagCbor> for Cid {
218 fn encode<W: Write>(&self, _: DagCbor, w: &mut W) -> Result<()> {
219 write_tag(w, 42)?;
220 let buf = self.to_bytes();
223 let len = buf.len();
224 write_u64(w, MajorKind::ByteString, len as u64 + 1)?;
225 w.write_all(&[0])?;
226 w.write_all(&buf[..len])?;
227 Ok(())
228 }
229}
230
231impl<T: Encode<DagCbor>> Encode<DagCbor> for Option<T> {
232 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
233 if let Some(value) = self {
234 value.encode(c, w)?;
235 } else {
236 write_null(w)?;
237 }
238 Ok(())
239 }
240}
241
242impl<T: Encode<DagCbor>> Encode<DagCbor> for Vec<T> {
243 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
244 write_u64(w, MajorKind::Array, self.len() as u64)?;
245 for value in self {
246 value.encode(c, w)?;
247 }
248 Ok(())
249 }
250}
251
252impl<T: Encode<DagCbor> + 'static> Encode<DagCbor> for BTreeMap<String, T> {
253 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
254 write_u64(w, MajorKind::Map, self.len() as u64)?;
255 let mut cbor_order = Vec::from_iter(self);
259 cbor_order.sort_unstable_by(|&(key_a, _), &(key_b, _)| {
260 match key_a.len().cmp(&key_b.len()) {
261 Ordering::Greater => Ordering::Greater,
262 Ordering::Less => Ordering::Less,
263 Ordering::Equal => key_a.cmp(key_b),
264 }
265 });
266 for (k, v) in cbor_order {
267 k.encode(c, w)?;
268 v.encode(c, w)?;
269 }
270 Ok(())
271 }
272}
273
274impl Encode<DagCbor> for Ipld {
275 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
276 match self {
277 Self::Null => write_null(w),
278 Self::Bool(b) => b.encode(c, w),
279 Self::Integer(i) => i.encode(c, w),
280 Self::Float(f) => f.encode(c, w),
281 Self::Bytes(b) => b.as_slice().encode(c, w),
282 Self::String(s) => s.encode(c, w),
283 Self::List(l) => l.encode(c, w),
284 Self::Map(m) => m.encode(c, w),
285 Self::Link(cid) => cid.encode(c, w),
286 }
287 }
288}
289
290impl<T: Encode<DagCbor>> Encode<DagCbor> for Arc<T> {
291 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
292 self.deref().encode(c, w)
293 }
294}
295
296impl Encode<DagCbor> for () {
297 fn encode<W: Write>(&self, _c: DagCbor, w: &mut W) -> Result<()> {
298 write_u8(w, MajorKind::Array, 0)?;
299 Ok(())
300 }
301}
302
303impl<A: Encode<DagCbor>> Encode<DagCbor> for (A,) {
304 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
305 write_u8(w, MajorKind::Array, 1)?;
306 self.0.encode(c, w)?;
307 Ok(())
308 }
309}
310
311impl<A: Encode<DagCbor>, B: Encode<DagCbor>> Encode<DagCbor> for (A, B) {
312 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
313 write_u8(w, MajorKind::Array, 2)?;
314 self.0.encode(c, w)?;
315 self.1.encode(c, w)?;
316 Ok(())
317 }
318}
319
320impl<A: Encode<DagCbor>, B: Encode<DagCbor>, C: Encode<DagCbor>> Encode<DagCbor> for (A, B, C) {
321 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
322 write_u8(w, MajorKind::Array, 3)?;
323 self.0.encode(c, w)?;
324 self.1.encode(c, w)?;
325 self.2.encode(c, w)?;
326 Ok(())
327 }
328}
329
330impl<A: Encode<DagCbor>, B: Encode<DagCbor>, C: Encode<DagCbor>, D: Encode<DagCbor>> Encode<DagCbor>
331 for (A, B, C, D)
332{
333 fn encode<W: Write>(&self, c: DagCbor, w: &mut W) -> Result<()> {
334 write_u8(w, MajorKind::Array, 4)?;
335 self.0.encode(c, w)?;
336 self.1.encode(c, w)?;
337 self.2.encode(c, w)?;
338 self.3.encode(c, w)?;
339 Ok(())
340 }
341}