1use std::io::{
12 Result,
13 Write,
14};
15
16use crate::codec::{
17 BigEndian,
18 BinaryCodec,
19 ByteOrder,
20 LittleEndian,
21};
22
23macro_rules! write_binary_value {
24 ($writer:expr, $value:expr, $ty:ty, $order:ty) => {
25 write_binary::<{ BinaryCodec::<$ty, $order>::REQUIRED_MIN_BUFFER_LEN }, _, _, _>(
26 $writer,
27 $value,
28 |bytes, value| {
29 unsafe { BinaryCodec::<$ty, $order>::write_unchecked(bytes, 0, value) }
31 },
32 )
33 };
34}
35
36pub trait BinaryWriteExt: Write {
38 #[inline]
40 fn write_u8(&mut self, value: u8) -> Result<()> {
41 write_binary_value!(self, value, u8, BigEndian)
42 }
43
44 #[inline]
46 fn write_i8(&mut self, value: i8) -> Result<()> {
47 write_binary_value!(self, value, i8, BigEndian)
48 }
49
50 #[inline]
52 fn write_u16(&mut self, value: u16, byte_order: ByteOrder) -> Result<()> {
53 match byte_order {
54 ByteOrder::BigEndian => self.write_u16_be(value),
55 ByteOrder::LittleEndian => self.write_u16_le(value),
56 }
57 }
58
59 #[inline]
61 fn write_u16_be(&mut self, value: u16) -> Result<()> {
62 write_binary_value!(self, value, u16, BigEndian)
63 }
64
65 #[inline]
67 fn write_u16_le(&mut self, value: u16) -> Result<()> {
68 write_binary_value!(self, value, u16, LittleEndian)
69 }
70
71 #[inline]
73 fn write_u32(&mut self, value: u32, byte_order: ByteOrder) -> Result<()> {
74 match byte_order {
75 ByteOrder::BigEndian => self.write_u32_be(value),
76 ByteOrder::LittleEndian => self.write_u32_le(value),
77 }
78 }
79
80 #[inline]
82 fn write_u32_be(&mut self, value: u32) -> Result<()> {
83 write_binary_value!(self, value, u32, BigEndian)
84 }
85
86 #[inline]
88 fn write_u32_le(&mut self, value: u32) -> Result<()> {
89 write_binary_value!(self, value, u32, LittleEndian)
90 }
91
92 #[inline]
94 fn write_u64(&mut self, value: u64, byte_order: ByteOrder) -> Result<()> {
95 match byte_order {
96 ByteOrder::BigEndian => self.write_u64_be(value),
97 ByteOrder::LittleEndian => self.write_u64_le(value),
98 }
99 }
100
101 #[inline]
103 fn write_u64_be(&mut self, value: u64) -> Result<()> {
104 write_binary_value!(self, value, u64, BigEndian)
105 }
106
107 #[inline]
109 fn write_u64_le(&mut self, value: u64) -> Result<()> {
110 write_binary_value!(self, value, u64, LittleEndian)
111 }
112
113 #[inline]
115 fn write_u128(&mut self, value: u128, byte_order: ByteOrder) -> Result<()> {
116 match byte_order {
117 ByteOrder::BigEndian => self.write_u128_be(value),
118 ByteOrder::LittleEndian => self.write_u128_le(value),
119 }
120 }
121
122 #[inline]
124 fn write_u128_be(&mut self, value: u128) -> Result<()> {
125 write_binary_value!(self, value, u128, BigEndian)
126 }
127
128 #[inline]
130 fn write_u128_le(&mut self, value: u128) -> Result<()> {
131 write_binary_value!(self, value, u128, LittleEndian)
132 }
133
134 #[inline]
136 fn write_i16(&mut self, value: i16, byte_order: ByteOrder) -> Result<()> {
137 match byte_order {
138 ByteOrder::BigEndian => self.write_i16_be(value),
139 ByteOrder::LittleEndian => self.write_i16_le(value),
140 }
141 }
142
143 #[inline]
145 fn write_i16_be(&mut self, value: i16) -> Result<()> {
146 write_binary_value!(self, value, i16, BigEndian)
147 }
148
149 #[inline]
151 fn write_i16_le(&mut self, value: i16) -> Result<()> {
152 write_binary_value!(self, value, i16, LittleEndian)
153 }
154
155 #[inline]
157 fn write_i32(&mut self, value: i32, byte_order: ByteOrder) -> Result<()> {
158 match byte_order {
159 ByteOrder::BigEndian => self.write_i32_be(value),
160 ByteOrder::LittleEndian => self.write_i32_le(value),
161 }
162 }
163
164 #[inline]
166 fn write_i32_be(&mut self, value: i32) -> Result<()> {
167 write_binary_value!(self, value, i32, BigEndian)
168 }
169
170 #[inline]
172 fn write_i32_le(&mut self, value: i32) -> Result<()> {
173 write_binary_value!(self, value, i32, LittleEndian)
174 }
175
176 #[inline]
178 fn write_i64(&mut self, value: i64, byte_order: ByteOrder) -> Result<()> {
179 match byte_order {
180 ByteOrder::BigEndian => self.write_i64_be(value),
181 ByteOrder::LittleEndian => self.write_i64_le(value),
182 }
183 }
184
185 #[inline]
187 fn write_i64_be(&mut self, value: i64) -> Result<()> {
188 write_binary_value!(self, value, i64, BigEndian)
189 }
190
191 #[inline]
193 fn write_i64_le(&mut self, value: i64) -> Result<()> {
194 write_binary_value!(self, value, i64, LittleEndian)
195 }
196
197 #[inline]
199 fn write_i128(&mut self, value: i128, byte_order: ByteOrder) -> Result<()> {
200 match byte_order {
201 ByteOrder::BigEndian => self.write_i128_be(value),
202 ByteOrder::LittleEndian => self.write_i128_le(value),
203 }
204 }
205
206 #[inline]
208 fn write_i128_be(&mut self, value: i128) -> Result<()> {
209 write_binary_value!(self, value, i128, BigEndian)
210 }
211
212 #[inline]
214 fn write_i128_le(&mut self, value: i128) -> Result<()> {
215 write_binary_value!(self, value, i128, LittleEndian)
216 }
217
218 #[inline]
220 fn write_f32(&mut self, value: f32, byte_order: ByteOrder) -> Result<()> {
221 match byte_order {
222 ByteOrder::BigEndian => self.write_f32_be(value),
223 ByteOrder::LittleEndian => self.write_f32_le(value),
224 }
225 }
226
227 #[inline]
229 fn write_f32_be(&mut self, value: f32) -> Result<()> {
230 write_binary_value!(self, value, f32, BigEndian)
231 }
232
233 #[inline]
235 fn write_f32_le(&mut self, value: f32) -> Result<()> {
236 write_binary_value!(self, value, f32, LittleEndian)
237 }
238
239 #[inline]
241 fn write_f64(&mut self, value: f64, byte_order: ByteOrder) -> Result<()> {
242 match byte_order {
243 ByteOrder::BigEndian => self.write_f64_be(value),
244 ByteOrder::LittleEndian => self.write_f64_le(value),
245 }
246 }
247
248 #[inline]
250 fn write_f64_be(&mut self, value: f64) -> Result<()> {
251 write_binary_value!(self, value, f64, BigEndian)
252 }
253
254 #[inline]
256 fn write_f64_le(&mut self, value: f64) -> Result<()> {
257 write_binary_value!(self, value, f64, LittleEndian)
258 }
259}
260
261impl<W> BinaryWriteExt for W where W: Write + ?Sized {}
262
263#[inline]
264fn write_binary<const N: usize, T, W, F>(writer: &mut W, value: T, encode: F) -> Result<()>
265where
266 W: Write + ?Sized,
267 F: FnOnce(&mut [u8], T),
268{
269 let mut bytes = [0u8; N];
270 encode(&mut bytes, value);
271 writer.write_all(&bytes)
272}