1use core::fmt;
6use core::mem::take;
7
8use musli::{Buf, Context};
9
10#[cfg(feature = "alloc")]
11use alloc::vec::Vec;
12
13pub const MAX_FIXED_BYTES_LEN: usize = 128;
15
16#[derive(Debug)]
18pub(crate) struct SliceOverflow {
19 n: usize,
20 capacity: usize,
21}
22
23impl fmt::Display for SliceOverflow {
24 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
25 let SliceOverflow { n, capacity } = self;
26
27 write!(
28 f,
29 "Tried to write {n} bytes to slice, with a remaining capacity of {capacity}"
30 )
31 }
32}
33
34pub trait Writer {
36 type Mut<'this>: Writer
47 where
48 Self: 'this;
49
50 fn borrow_mut(&mut self) -> Self::Mut<'_>;
52
53 fn write_buffer<C, B>(&mut self, cx: &C, buffer: B) -> Result<(), C::Error>
55 where
56 C: ?Sized + Context,
57 B: Buf;
58
59 fn write_bytes<C>(&mut self, cx: &C, bytes: &[u8]) -> Result<(), C::Error>
61 where
62 C: ?Sized + Context;
63
64 #[inline]
66 fn write_byte<C>(&mut self, cx: &C, b: u8) -> Result<(), C::Error>
67 where
68 C: ?Sized + Context,
69 {
70 self.write_bytes(cx, &[b])
71 }
72}
73
74impl<W> Writer for &mut W
75where
76 W: ?Sized + Writer,
77{
78 type Mut<'this> = &'this mut W where Self: 'this;
79
80 #[inline]
81 fn borrow_mut(&mut self) -> Self::Mut<'_> {
82 self
83 }
84
85 #[inline]
86 fn write_buffer<C, B>(&mut self, cx: &C, buffer: B) -> Result<(), C::Error>
87 where
88 C: ?Sized + Context,
89 B: Buf,
90 {
91 (*self).write_buffer(cx, buffer)
92 }
93
94 #[inline]
95 fn write_bytes<C>(&mut self, cx: &C, bytes: &[u8]) -> Result<(), C::Error>
96 where
97 C: ?Sized + Context,
98 {
99 (*self).write_bytes(cx, bytes)
100 }
101
102 #[inline]
103 fn write_byte<C>(&mut self, cx: &C, b: u8) -> Result<(), C::Error>
104 where
105 C: ?Sized + Context,
106 {
107 (*self).write_byte(cx, b)
108 }
109}
110
111#[cfg(feature = "alloc")]
112impl Writer for Vec<u8> {
113 type Mut<'this> = &'this mut Self where Self: 'this;
114
115 #[inline]
116 fn borrow_mut(&mut self) -> Self::Mut<'_> {
117 self
118 }
119
120 #[inline]
121 fn write_buffer<C, B>(&mut self, cx: &C, buffer: B) -> Result<(), C::Error>
122 where
123 C: ?Sized + Context,
124 B: Buf,
125 {
126 self.write_bytes(cx, buffer.as_slice())
128 }
129
130 #[inline]
131 fn write_bytes<C>(&mut self, cx: &C, bytes: &[u8]) -> Result<(), C::Error>
132 where
133 C: ?Sized + Context,
134 {
135 self.extend_from_slice(bytes);
136 cx.advance(bytes.len());
137 Ok(())
138 }
139
140 #[inline]
141 fn write_byte<C>(&mut self, cx: &C, b: u8) -> Result<(), C::Error>
142 where
143 C: ?Sized + Context,
144 {
145 self.push(b);
146 cx.advance(1);
147 Ok(())
148 }
149}
150
151impl Writer for &mut [u8] {
152 type Mut<'this> = &'this mut Self where Self: 'this;
153
154 #[inline]
155 fn borrow_mut(&mut self) -> Self::Mut<'_> {
156 self
157 }
158
159 #[inline]
160 fn write_buffer<C, B>(&mut self, cx: &C, buffer: B) -> Result<(), C::Error>
161 where
162 C: ?Sized + Context,
163 B: Buf,
164 {
165 self.write_bytes(cx, buffer.as_slice())
167 }
168
169 #[inline]
170 fn write_bytes<C>(&mut self, cx: &C, bytes: &[u8]) -> Result<(), C::Error>
171 where
172 C: ?Sized + Context,
173 {
174 if self.len() < bytes.len() {
175 return Err(cx.message(SliceOverflow {
176 n: bytes.len(),
177 capacity: self.len(),
178 }));
179 }
180
181 let next = take(self);
182 let (this, next) = next.split_at_mut(bytes.len());
183 this.copy_from_slice(bytes);
184 *self = next;
185 Ok(())
186 }
187
188 #[inline]
189 fn write_byte<C>(&mut self, cx: &C, b: u8) -> Result<(), C::Error>
190 where
191 C: ?Sized + Context,
192 {
193 if self.is_empty() {
194 return Err(cx.message(format_args!(
195 "Buffer overflow, remaining is {} while tried to write 1",
196 self.len()
197 )));
198 }
199
200 self[0] = b;
201 *self = &mut take(self)[1..];
202 Ok(())
203 }
204}
205
206pub struct BufWriter<T> {
208 buf: T,
209}
210
211impl<T> BufWriter<T> {
212 pub fn new(buf: T) -> Self {
214 Self { buf }
215 }
216
217 pub fn into_inner(self) -> T {
219 self.buf
220 }
221}
222
223impl<T> Writer for BufWriter<T>
224where
225 T: Buf,
226{
227 type Mut<'this> = &'this mut Self
228 where
229 Self: 'this;
230
231 #[inline(always)]
232 fn borrow_mut(&mut self) -> Self::Mut<'_> {
233 self
234 }
235
236 #[inline(always)]
237 fn write_buffer<C, B>(&mut self, cx: &C, buffer: B) -> Result<(), C::Error>
238 where
239 C: ?Sized + Context,
240 B: Buf,
241 {
242 if !self.buf.write(buffer.as_slice()) {
243 return Err(cx.message("Buffer overflow"));
244 }
245
246 Ok(())
247 }
248
249 #[inline(always)]
250 fn write_bytes<C>(&mut self, cx: &C, bytes: &[u8]) -> Result<(), C::Error>
251 where
252 C: ?Sized + Context,
253 {
254 if !self.buf.write(bytes) {
255 return Err(cx.message("Buffer overflow"));
256 }
257
258 Ok(())
259 }
260}