wavesplatform/
bytebuffer.rs

1use crate::transaction::{Asset, DataEntry};
2use base58::*;
3
4pub(crate) struct Buffer {
5    buf: Vec<u8>,
6}
7
8impl Buffer {
9    pub fn new() -> Buffer {
10        Buffer { buf: Vec::new() }
11    }
12
13    #[allow(dead_code)]
14    pub fn from_bytes(b: &[u8]) -> Buffer {
15        Buffer { buf: Vec::from(b) }
16    }
17
18    pub fn bytes(self: &mut Buffer, b: &[u8]) -> &mut Buffer {
19        self.buf.extend_from_slice(b);
20        self
21    }
22
23    pub fn byte(self: &mut Buffer, b: u8) -> &mut Buffer {
24        self.buf.push(b);
25        self
26    }
27
28    pub fn size(&mut self, n: usize) -> &mut Buffer {
29        let bytes = [((n >> 8) & 0xff) as u8, (n & 0xff) as u8];
30        self.bytes(&bytes)
31    }
32
33    pub fn long(&mut self, n: u64) -> &mut Buffer {
34        let bytes = [
35            ((n >> 56) & 0xff) as u8,
36            ((n >> 48) & 0xff) as u8,
37            ((n >> 40) & 0xff) as u8,
38            ((n >> 32) & 0xff) as u8,
39            ((n >> 24) & 0xff) as u8,
40            ((n >> 16) & 0xff) as u8,
41            ((n >> 8) & 0xff) as u8,
42            (n & 0xff) as u8,
43        ];
44        self.bytes(&bytes)
45    }
46
47    pub fn boolean(&mut self, b: bool) -> &mut Buffer {
48        let val = if b { 1 } else { 0 };
49        self.buf.push(val);
50        self
51    }
52
53    pub fn recipient(&mut self, chain_id: u8, recipient: &str) -> &mut Buffer {
54        if recipient.len() <= 30 {
55            // assume an alias
56            self.byte(0x02)
57                .byte(chain_id)
58                .size(recipient.len())
59                .bytes(recipient.as_bytes())
60        } else {
61            self.bytes(recipient.from_base58().unwrap().as_slice())
62        }
63    }
64
65    pub fn array(&mut self, arr: &[u8]) -> &mut Buffer {
66        self.size(arr.len()).bytes(arr)
67    }
68
69    pub fn array_opt(&mut self, arr: Option<&[u8]>) -> &mut Buffer {
70        self.array(arr.unwrap_or(&[]))
71    }
72
73    pub fn asset(&mut self, asset: &Asset) -> &mut Buffer {
74        self.bytes(&asset.to_bytes())
75    }
76
77    pub fn asset_opt(&mut self, asset: &Option<&Asset>) -> &mut Buffer {
78        match asset {
79            Some(aid) => self.byte(1).asset(aid),
80            None => self.byte(0),
81        }
82    }
83
84    pub fn data_entry(&mut self, e: &DataEntry) -> &mut Buffer {
85        match *e {
86            DataEntry::Integer(key, val) => self.array(key.as_bytes()).byte(0).long(val),
87            DataEntry::Boolean(key, val) => self.array(key.as_bytes()).byte(1).boolean(val),
88            DataEntry::Binary(key, val) => self.array(key.as_bytes()).byte(2).array(val),
89            DataEntry::String(key, val) => self.array(key.as_bytes()).byte(3).array(val.as_bytes()),
90        }
91    }
92
93    pub fn as_slice(&self) -> &[u8] {
94        self.buf.as_slice()
95    }
96}