1use crate::types;
2use crate::types::JceHeader;
3use bytes::BufMut;
4
5pub fn write_header<B: BufMut>(buf: &mut B, JceHeader { val_type, tag }: JceHeader) {
6 if tag < 0xF {
7 buf.put_u8((tag << 4) | val_type)
8 } else {
9 buf.put_u8(val_type | 0xF0);
10 buf.put_u8(tag);
11 }
12}
13
14pub fn write_empty<B: BufMut>(buf: &mut B, tag: u8) {
15 write_header(
16 buf,
17 JceHeader {
18 val_type: types::EMPTY,
19 tag,
20 },
21 );
22}
23
24pub fn write_type<B: BufMut>(buf: &mut B, t: u8) {
25 buf.put_u8(t);
26}
27
28pub fn write_len<B: BufMut>(buf: &mut B, len: usize) {
29 if let Ok(len) = u8::try_from(len) {
30 buf.put_u8(types::BYTE);
31 buf.put_u8(len);
32 } else if let Ok(len) = u16::try_from(len) {
33 buf.put_u8(types::SHORT);
34 buf.put_u16(len);
35 } else if let Ok(len) = u32::try_from(len) {
36 buf.put_u8(types::INT);
37 buf.put_u32(len);
38 } else if let Ok(len) = u64::try_from(len) {
39 buf.put_u8(types::LONG);
40 buf.put_u64(len);
41 } else {
42 unreachable!();
43 }
44}
45
46pub fn len_bytes(len: usize) -> usize {
47 const U8: usize = u8::MAX as usize;
48 const U81: usize = U8 + 1;
49 const U16: usize = u16::MAX as usize;
50 const U161: usize = U16 + 1;
51 const U32: usize = u32::MAX as usize;
52 const U321: usize = U32 + 1;
53 const U64: usize = u64::MAX as usize;
54
55 match len {
56 0..=U8 => 1,
57 U81..=U16 => 2,
58 U161..=U32 => 4,
59 U321..=U64 => 8,
60 _ => unreachable!(),
61 }
62}