• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

vigna / dsi-bitstream-rs / 21401683867

27 Jan 2026 02:46PM UTC coverage: 54.927% (+0.9%) from 54.058%
21401683867

push

github

vigna
Table file

28 of 28 new or added lines in 1 file covered. (100.0%)

29 existing lines in 2 files now uncovered.

2079 of 3785 relevant lines covered (54.93%)

2668396.38 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

80.95
/src/codes/params.rs
1
/*
2
 * SPDX-FileCopyrightText: 2023 Tommaso Fontana
3
 * SPDX-FileCopyrightText: 2023 Inria
4
 * SPDX-FileCopyrightText: 2023 Sebastiano Vigna
5
 *
6
 * SPDX-License-Identifier: Apache-2.0 OR LGPL-2.1-or-later
7
 */
8

9
/*!
10

11
Mechanisms for selecting parameters.
12

13
Traits and structures in this file are of no interest for the standard
14
user. Their purpose is to provide a systematic way, and in particular
15
a default way, to select parameters for parameterized traits
16
such as [`GammaReadParam`] and [`GammaWriteParam`].
17

18
The traits and structure in this module work closely with the
19
bitstream readers and writers in [`impls`](crate::impls), which have an
20
additional type parameter `RP`/`WP` that must
21
implement marker traits [`ReadParams`] or [`WriteParams`], respectively.
22
The type is then used as a selector type to provide blanket implementations
23
of parameterless traits in [`codes`](crate::codes) such as [`GammaRead`],
24
[`GammaWrite`], [`DeltaRead`], [`DeltaWrite`], and so on.
25

26
This module provides default selector types [`DefaultReadParams`] and [`DefaultWriteParams`]
27
which are also the default value for the parameter `RP`/`WP` in the bitstream
28
readers and writers in [`crate::impls`]. Type-selected blanket implementations
29
of all parameterless traits in [`crate::codes`] are provided for the bitstream
30
readers and writers in [`impls`](crate::impls). Thus, if you not specify a value for the
31
parameter `RP`/`WP`, you will obtain automatically
32
the blanket implementations for parameterless traits contained in this module.
33

34
However, you can also create new selector types implementing [`ReadParams`]/[`WriteParams`] and
35
write blanket implementations for the bitstream readers and writers in [`crate::impls`]
36
where `RP`/`WP` is set to your selector types. Then, by specifying your type as value of the
37
parameter `RP`/`WP` when creating such readers and writers you will use
38
automatically your blanket implementations instead of the ones provided by this module.
39

40
Note that the default implementations provided by this module are targeted at
41
`u32` read words and `u64` write words. If you use different word sizes,
42
you may want to write your own selector types.
43

44
*/
45

46
use crate::codes::*;
47
use crate::impls::*;
48
use crate::traits::*;
49
use common_traits::*;
50
use core::error::Error;
51
#[cfg(feature = "mem_dbg")]
52
use mem_dbg::{MemDbg, MemSize};
53

54
/// Marker trait for read-parameters selector types.
55
///
56
/// Note that in principle marker traits are not necessary to use
57
/// selector types, but they are useful to avoid that the user specifies
58
/// a nonsensical type, and to document the meaning of type parameters.
59
pub trait ReadParams {}
60

61
/// A selector type for read parameters providing reasonable defaults.
62
///
63
/// If you want to optimize these choices for your architecture, we suggest to
64
/// run the benchmarks in the `benchmarks` directory and write your
65
/// own implementation.
66
#[derive(Debug, Clone)]
67
#[cfg_attr(feature = "mem_dbg", derive(MemDbg, MemSize))]
68
pub struct DefaultReadParams;
69
impl ReadParams for DefaultReadParams {}
70

71
macro_rules! impl_default_read_codes {
72
    ($($endianess:ident),*) => {$(
73
        impl<WR: WordRead> GammaRead<$endianess>
74
            for BufBitReader<$endianess, WR, DefaultReadParams>
75
        where
76
            WR:: Word: DoubleType + UpcastableInto<u64>,
77
            <WR::Word as DoubleType>::DoubleType: CastableInto<u64>,
78
        {
79
            #[inline(always)]
80
            fn read_gamma(&mut self) -> Result<u64, Self::Error> {
12,048,291✔
81
                // From our tests on all architectures ɣ codes are faster
82
                // without tables
83
                self.read_gamma_param::<false>()
24,096,582✔
84
            }
85
        }
86

87
        impl<WR: WordRead> DeltaRead<$endianess>
88
            for BufBitReader<$endianess, WR, DefaultReadParams>
89
        where
90
            WR:: Word: DoubleType + UpcastableInto<u64>,
91
            <WR::Word as DoubleType>::DoubleType: CastableInto<u64>,
92
        {
93
            #[inline(always)]
94
            fn read_delta(&mut self) -> Result<u64, Self::Error> {
12,004,457✔
95
                self.read_delta_param::<false, true>()
24,008,914✔
96
            }
97
        }
98

99
        impl<WR: WordRead> OmegaRead<$endianess>
100
            for BufBitReader<$endianess, WR, DefaultReadParams>
101
        where
102
            WR:: Word: DoubleType + UpcastableInto<u64>,
103
            <WR::Word as DoubleType>::DoubleType: CastableInto<u64>,
104
        {
105
            #[inline(always)]
106
            fn read_omega(&mut self) -> Result<u64, Self::Error> {
4,376✔
107
                self.read_omega_param::<true>()
8,752✔
108
            }
109
        }
110

111
        impl<WR: WordRead> ZetaRead<$endianess>
112
            for BufBitReader<$endianess, WR, DefaultReadParams>
113
        where
114
            WR:: Word: DoubleType + UpcastableInto<u64>,
115
            <WR::Word as DoubleType>::DoubleType: CastableInto<u64>,
116
        {
117
            #[inline(always)]
118
            fn read_zeta(&mut self, k: usize) -> Result<u64, Self::Error> {
34,849✔
119
                self.read_zeta_param(k)
104,547✔
120
            }
121

122
            #[inline(always)]
123
            fn read_zeta3(&mut self) -> Result<u64, Self::Error> {
4,357✔
124
                self.read_zeta3_param::<true>()
8,714✔
125
            }
126
        }
127

128
        impl<WR: WordRead> PiRead<$endianess>
129
            for BufBitReader<$endianess, WR, DefaultReadParams>
130
        where
131
            WR:: Word: DoubleType + UpcastableInto<u64>,
132
            <WR::Word as DoubleType>::DoubleType: CastableInto<u64>,
133
        {
134
            #[inline(always)]
135
            fn read_pi(&mut self, k: usize) -> Result<u64, Self::Error> {
40,589✔
136
                self.read_pi_param(k)
121,767✔
137
            }
138

139
            #[inline(always)]
140
            fn read_pi2(&mut self) -> Result<u64, Self::Error> {
6,534✔
141
                self.read_pi2_param::<true>()
13,068✔
142
            }
143
        }
144

145
        impl<E: Error + Send + Sync + 'static, WR: WordRead<Error = E, Word = u64> + WordSeek<Error = E>> GammaRead<$endianess>
146
            for BitReader<$endianess, WR, DefaultReadParams>
147
        where
148
            WR:: Word: DoubleType + UpcastableInto<u64>,
149
            <WR::Word as DoubleType>::DoubleType: CastableInto<u64>,
150
        {
151
            #[inline(always)]
152
            fn read_gamma(&mut self) -> Result<u64, Self::Error> {
138✔
153
                // From our tests, the ARM architecture is faster
154
                // without tables for ɣ codes.
155
                self.read_gamma_param::<false>()
276✔
156
            }
157
        }
158

159
        impl<E: Error + Send + Sync + 'static, WR: WordRead<Error = E, Word = u64> + WordSeek<Error = E>> DeltaRead<$endianess>
160
            for BitReader<$endianess, WR, DefaultReadParams>
161
        where
162
            WR:: Word: DoubleType + UpcastableInto<u64>,
163
            <WR::Word as DoubleType>::DoubleType: CastableInto<u64>,
164
        {
165
            #[inline(always)]
UNCOV
166
            fn read_delta(&mut self) -> Result<u64, Self::Error> {
×
UNCOV
167
                self.read_delta_param::<false, true>()
×
168
            }
169
        }
170

171
        impl<E: Error + Send + Sync + 'static, WR: WordRead<Error = E, Word = u64> + WordSeek<Error = E>> OmegaRead<$endianess>
172
            for BitReader<$endianess, WR, DefaultReadParams>
173
        where
174
            WR:: Word: DoubleType + UpcastableInto<u64>,
175
            <WR::Word as DoubleType>::DoubleType: CastableInto<u64>,
176
        {
177
            #[inline(always)]
178
            fn read_omega(&mut self) -> Result<u64, Self::Error> {
20✔
179
                self.read_omega_param::<true>()
40✔
180
            }
181
        }
182

183
        impl<E: Error + Send + Sync + 'static, WR: WordRead<Error = E, Word = u64> + WordSeek<Error = E>> ZetaRead<$endianess>
184
            for BitReader<$endianess, WR, DefaultReadParams>
185
        where
186
            WR:: Word: DoubleType + UpcastableInto<u64>,
187
            <WR::Word as DoubleType>::DoubleType: CastableInto<u64>,
188
        {
189
            #[inline(always)]
UNCOV
190
            fn read_zeta(&mut self, k: usize) -> Result<u64, Self::Error> {
×
UNCOV
191
                self.read_zeta_param(k)
×
192
            }
193

194
            #[inline(always)]
UNCOV
195
            fn read_zeta3(&mut self) -> Result<u64, Self::Error> {
×
UNCOV
196
                self.read_zeta3_param::<true>()
×
197
            }
198
        }
199

200
        impl<E: Error + Send + Sync + 'static, WR: WordRead<Error = E, Word = u64> + WordSeek<Error = E>> PiRead<$endianess>
201
            for BitReader<$endianess, WR, DefaultReadParams>
202
        where
203
            WR:: Word: DoubleType + UpcastableInto<u64>,
204
            <WR::Word as DoubleType>::DoubleType: CastableInto<u64>,
205
        {
206
            #[inline(always)]
207
            fn read_pi(&mut self, k: usize) -> Result<u64, Self::Error> {
296✔
208
                self.read_pi_param(k)
888✔
209
            }
210

211
            #[inline(always)]
UNCOV
212
            fn read_pi2(&mut self) -> Result<u64, Self::Error> {
×
UNCOV
213
                self.read_pi2_param::<true>()
×
214
            }
215
        }
216
    )*};
217
}
218

219
impl_default_read_codes! {LittleEndian, BigEndian}
220

221
/// Marker trait for write-parameters selector types.
222
///
223
/// Note that in principle marker traits are not necessary to use
224
/// selector types, but they are useful to avoid that the user specifies
225
/// a nonsensical type, and to document the meaning of type parameters.
226
pub trait WriteParams {}
227

228
/// A selector type for write parameters providing reasonable defaults.
229
///
230
/// If you want to optimize these choices for your architecture, we suggest to
231
/// run the benchmarks in the `benchmarks` directory and write your
232
/// own implementation.
233
#[derive(Debug, Clone)]
234
#[cfg_attr(feature = "mem_dbg", derive(MemDbg, MemSize))]
235
pub struct DefaultWriteParams;
236
impl WriteParams for DefaultWriteParams {}
237

238
macro_rules! impl_default_write_codes {
239
    ($($endianess:ident),*) => {$(
240
        impl<WR: WordWrite> GammaWrite<$endianess>
241
            for BufBitWriter<$endianess, WR, DefaultWriteParams>
242
            where u64: CastableInto<WR::Word>,
243
        {
244
            #[inline(always)]
245
            fn write_gamma(&mut self, value: u64) -> Result<usize, Self::Error> {
20,052,668✔
246
                self.write_gamma_param::<true>(value)
60,158,004✔
247
            }
248
        }
249

250
        impl<WR: WordWrite, DC: WriteParams> DeltaWrite<$endianess>
251
            for BufBitWriter<$endianess, WR, DC>
252
            where u64: CastableInto<WR::Word>,
253
        {
254
            #[inline(always)]
255
            fn write_delta(&mut self, value: u64) -> Result<usize, Self::Error> {
20,004,494✔
256
                self.write_delta_param::<true, true>(value)
60,013,482✔
257
            }
258
        }
259

260
        impl<WR: WordWrite, WP: WriteParams> OmegaWrite<$endianess>
261
            for BufBitWriter<$endianess, WR, WP>
262
            where u64: CastableInto<WR::Word>,
263
        {
264
            #[inline(always)]
265
            fn write_omega(&mut self, value: u64) -> Result<usize, Self::Error> {
4,400✔
266
                self.write_omega_param::<true>(value)
13,200✔
267
            }
268
        }
269

270
        impl<WR: WordWrite, DC: WriteParams> ZetaWrite<$endianess>
271
            for BufBitWriter<$endianess, WR, DC>
272
            where u64: CastableInto<WR::Word>,
273
        {
274
            #[inline(always)]
275
            fn write_zeta(&mut self, value: u64, k: usize) -> Result<usize, Self::Error> {
30,815✔
276
                self.write_zeta_param::<true>(value, k)
123,260✔
277
            }
278

279
            #[inline(always)]
280
            fn write_zeta3(&mut self, value: u64) -> Result<usize, Self::Error> {
4,379✔
281
                self.write_zeta3_param::<true>(value)
13,137✔
282
            }
283
        }
284

285
        impl<WR: WordWrite, DC: WriteParams> PiWrite<$endianess>
286
            for BufBitWriter<$endianess, WR, DC>
287
            where u64: CastableInto<WR::Word>,
288
        {
289
            #[inline(always)]
290
            fn write_pi(&mut self, value: u64, k: usize) -> Result<usize, Self::Error> {
40,906✔
291
                self.write_pi_param::<true>(value, k)
163,624✔
292
            }
293

294
            #[inline(always)]
295
            fn write_pi2(&mut self, value: u64) -> Result<usize, Self::Error> {
6,534✔
296
                self.write_pi2_param::<true>(value)
19,602✔
297
            }
298
        }
299

300
    )*};
301
}
302

303
impl_default_write_codes! {LittleEndian, BigEndian}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc