1//! Buffer wrappers implementing default so we can allocate the buffers with `Box::default()`
2//! to avoid stack copies. Box::new() doesn't at the moment, and using a vec means we would lose
3//! static length info.
4
5use crate::deflate::core::{LZ_DICT_SIZE, MAX_MATCH_LEN};
6
7/// Size of the buffer of lz77 encoded data.
8pub const LZ_CODE_BUF_SIZE: usize = 64 * 1024;
9/// Size of the output buffer.
10pub const OUT_BUF_SIZE: usize = (LZ_CODE_BUF_SIZE * 13) / 10;
11pub const LZ_DICT_FULL_SIZE: usize = LZ_DICT_SIZE + MAX_MATCH_LEN - 1 + 1;
12
13/// Size of hash values in the hash chains.
14pub const LZ_HASH_BITS: i32 = 15;
15/// How many bits to shift when updating the current hash value.
16pub const LZ_HASH_SHIFT: i32 = (LZ_HASH_BITS + 2) / 3;
17/// Size of the chained hash tables.
18pub const LZ_HASH_SIZE: usize = 1 << LZ_HASH_BITS;
19
20#[inline]
21pub fn update_hash(current_hash: u16, byte: u8) -> u16 {
22 ((current_hash << LZ_HASH_SHIFT) ^ u16::from(byte)) & (LZ_HASH_SIZE as u16 - 1)
23}
24
25pub struct HashBuffers {
26 pub dict: [u8; LZ_DICT_FULL_SIZE],
27 pub next: [u16; LZ_DICT_SIZE],
28 pub hash: [u16; LZ_DICT_SIZE],
29}
30
31impl HashBuffers {
32 #[inline]
33 pub fn reset(&mut self) {
34 *self = HashBuffers::default();
35 }
36}
37
38impl Default for HashBuffers {
39 fn default() -> HashBuffers {
40 HashBuffers {
41 dict: [0; LZ_DICT_FULL_SIZE],
42 next: [0; LZ_DICT_SIZE],
43 hash: [0; LZ_DICT_SIZE],
44 }
45 }
46}
47
48pub struct LocalBuf {
49 pub b: [u8; OUT_BUF_SIZE],
50}
51
52impl Default for LocalBuf {
53 fn default() -> LocalBuf {
54 LocalBuf {
55 b: [0; OUT_BUF_SIZE],
56 }
57 }
58}
59