mcproto_rs/
utils.rs

1use crate::{DeserializeErr, DeserializeResult};
2use alloc::string::String;
3
4pub fn take(amount: usize, data: &[u8]) -> DeserializeResult<&[u8]> {
5    if data.len() < amount {
6        Err(DeserializeErr::Eof)
7    } else {
8        Ok(data.split_at(amount).into())
9    }
10}
11
12pub fn hex(data: &[u8]) -> String {
13    let mut str = String::with_capacity(data.len() * 2);
14    for byte_ref in data {
15        let byte = *byte_ref;
16        str.push(hex_char_for(byte >> 4));
17        str.push(hex_char_for(byte & 0xF));
18    }
19    str
20}
21
22const ZERO_ASCII_CODE: u8 = 48;
23const LOWER_A_ASCII_CODE: u8 = 97;
24
25fn hex_char_for(half: u8) -> char {
26    if half > 0xF {
27        panic!("not defined for > 0xF (operates on half a byte)");
28    }
29
30    if half < 10 {
31        (half + ZERO_ASCII_CODE) as char
32    } else {
33        (half + (LOWER_A_ASCII_CODE - 10)) as char
34    }
35}
36
37pub fn parse_hex_char(data: u8) -> Option<u8> {
38    const UPPER_A_ASCII_CODE: u8 = 65;
39    const LOWER_F_ASCII_CODE: u8 = 102;
40    const UPPER_F_ASCII_CODE: u8 = 70;
41    const NINE_ASCII_CODE: u8 = 57;
42
43    if data >= LOWER_A_ASCII_CODE {
44        if data > LOWER_F_ASCII_CODE {
45            None
46        } else {
47            Some(10 + (data - LOWER_A_ASCII_CODE))
48        }
49    } else if data >= UPPER_A_ASCII_CODE {
50        if data > UPPER_F_ASCII_CODE {
51            None
52        } else {
53            Some(10 + (data - UPPER_A_ASCII_CODE))
54        }
55    } else if data >= ZERO_ASCII_CODE {
56        if data > NINE_ASCII_CODE {
57            None
58        } else {
59            Some(data - ZERO_ASCII_CODE)
60        }
61    } else {
62        None
63    }
64}