1#![no_std]
2#![cfg_attr(docsrs, feature(doc_auto_cfg))]
3#![doc = include_str!("../README.md")]
4#![deny(unsafe_code)]
5#![warn(
6 clippy::unwrap_used,
7 missing_docs,
8 rust_2018_idioms,
9 trivial_casts,
10 trivial_numeric_casts,
11 unused_qualifications
12)]
13
14#[cfg(feature = "alloc")]
15extern crate alloc;
16
17#[cfg(feature = "alloc")]
18use alloc::{format, string::String};
19
20use core::fmt;
21
22use digest::Update;
23use serde::{
24 ser::{
25 self, SerializeMap, SerializeSeq, SerializeStruct, SerializeStructVariant, SerializeTuple,
26 SerializeTupleStruct, SerializeTupleVariant,
27 },
28 Serialize, Serializer,
29};
30
31pub struct HashingSerializer<'a, T: Update> {
33 pub digest: &'a mut T,
35}
36
37#[derive(Debug, PartialEq, Eq, Clone)]
39pub enum Error {
40 UndefinedSequenceLength,
42
43 SequenceLengthTooLarge,
47
48 CannotCollectStr,
52
53 CustomErrorNoAlloc,
58
59 #[cfg(feature = "alloc")]
61 CustomError(String),
62}
63
64#[cfg(feature = "alloc")]
65impl ser::Error for Error {
66 fn custom<T: fmt::Display>(msg: T) -> Self {
67 Self::CustomError(format!("{}", msg))
68 }
69}
70
71#[cfg(not(feature = "alloc"))]
72impl ser::Error for Error {
73 fn custom<T: fmt::Display>(_msg: T) -> Self {
74 Self::CustomErrorNoAlloc
75 }
76}
77
78impl ser::StdError for Error {}
79
80impl fmt::Display for Error {
81 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
82 write!(f, "{:?}", self)
83 }
84}
85
86fn try_into_sequence_length(len: usize) -> Result<u128, Error> {
89 u128::try_from(len)
90 .ok()
91 .ok_or(Error::SequenceLengthTooLarge)
92}
93
94impl<'a, T: Update> Serializer for HashingSerializer<'a, T> {
95 type Ok = ();
96 type Error = Error;
97 type SerializeSeq = Self;
98 type SerializeTuple = Self;
99 type SerializeTupleStruct = Self;
100 type SerializeTupleVariant = Self;
101 type SerializeMap = Self;
102 type SerializeStruct = Self;
103 type SerializeStructVariant = Self;
104
105 fn serialize_bool(self, v: bool) -> Result<Self::Ok, Self::Error> {
106 self.digest.update(&(v as u8).to_be_bytes());
107 Ok(())
108 }
109
110 fn serialize_i8(self, v: i8) -> Result<Self::Ok, Self::Error> {
111 self.digest.update(&v.to_be_bytes());
112 Ok(())
113 }
114
115 fn serialize_i16(self, v: i16) -> Result<Self::Ok, Self::Error> {
116 self.digest.update(&v.to_be_bytes());
117 Ok(())
118 }
119
120 fn serialize_i32(self, v: i32) -> Result<Self::Ok, Self::Error> {
121 self.digest.update(&v.to_be_bytes());
122 Ok(())
123 }
124
125 fn serialize_i64(self, v: i64) -> Result<Self::Ok, Self::Error> {
126 self.digest.update(&v.to_be_bytes());
127 Ok(())
128 }
129
130 fn serialize_u8(self, v: u8) -> Result<Self::Ok, Self::Error> {
131 self.digest.update(&v.to_be_bytes());
132 Ok(())
133 }
134
135 fn serialize_u16(self, v: u16) -> Result<Self::Ok, Self::Error> {
136 self.digest.update(&v.to_be_bytes());
137 Ok(())
138 }
139
140 fn serialize_u32(self, v: u32) -> Result<Self::Ok, Self::Error> {
141 self.digest.update(&v.to_be_bytes());
142 Ok(())
143 }
144
145 fn serialize_u64(self, v: u64) -> Result<Self::Ok, Self::Error> {
146 self.digest.update(&v.to_be_bytes());
147 Ok(())
148 }
149
150 fn serialize_f32(self, v: f32) -> Result<Self::Ok, Self::Error> {
151 self.digest.update(&v.to_be_bytes());
152 Ok(())
153 }
154
155 fn serialize_f64(self, v: f64) -> Result<Self::Ok, Self::Error> {
156 self.digest.update(&v.to_be_bytes());
157 Ok(())
158 }
159 fn serialize_char(self, v: char) -> Result<Self::Ok, Self::Error> {
160 self.digest.update(&u64::from(v).to_be_bytes());
163 Ok(())
164 }
165
166 fn serialize_str(self, v: &str) -> Result<Self::Ok, Self::Error> {
167 self.digest.update(v.as_ref());
168 Ok(())
169 }
170
171 fn serialize_bytes(self, v: &[u8]) -> Result<Self::Ok, Self::Error> {
172 self.digest.update(v);
173 Ok(())
174 }
175
176 fn serialize_none(self) -> Result<Self::Ok, Self::Error> {
177 self.digest.update(&[0]);
178 Ok(())
179 }
180
181 fn serialize_some<V: ?Sized + Serialize>(self, value: &V) -> Result<Self::Ok, Self::Error> {
182 self.digest.update(&[1]);
183 value.serialize(self)
184 }
185
186 fn serialize_unit(self) -> Result<Self::Ok, Self::Error> {
187 Ok(())
188 }
189
190 fn serialize_unit_struct(self, _name: &'static str) -> Result<Self::Ok, Self::Error> {
191 Ok(())
192 }
193
194 fn serialize_unit_variant(
195 self,
196 _name: &'static str,
197 variant_index: u32,
198 _variant: &'static str,
199 ) -> Result<Self::Ok, Self::Error> {
200 self.digest.update(&variant_index.to_be_bytes());
201 Ok(())
202 }
203
204 fn serialize_newtype_struct<V: ?Sized + Serialize>(
205 self,
206 _name: &'static str,
207 value: &V,
208 ) -> Result<Self::Ok, Self::Error> {
209 value.serialize(self)
210 }
211
212 fn serialize_newtype_variant<V: ?Sized + Serialize>(
213 self,
214 _name: &'static str,
215 variant_index: u32,
216 _variant: &'static str,
217 value: &V,
218 ) -> Result<Self::Ok, Self::Error> {
219 self.digest.update(&variant_index.to_be_bytes());
220 value.serialize(self)
221 }
222
223 fn serialize_seq(self, len: Option<usize>) -> Result<Self::SerializeSeq, Self::Error> {
224 let len = len.ok_or(Error::UndefinedSequenceLength)?;
225 self.digest
226 .update(&try_into_sequence_length(len)?.to_be_bytes());
227 Ok(self)
228 }
229
230 fn serialize_tuple(self, len: usize) -> Result<Self::SerializeTuple, Self::Error> {
231 self.digest
232 .update(&try_into_sequence_length(len)?.to_be_bytes());
233 Ok(self)
234 }
235
236 fn serialize_tuple_struct(
237 self,
238 _name: &'static str,
239 len: usize,
240 ) -> Result<Self::SerializeTupleStruct, Self::Error> {
241 self.digest
242 .update(&try_into_sequence_length(len)?.to_be_bytes());
243 Ok(self)
244 }
245
246 fn serialize_tuple_variant(
247 self,
248 _name: &'static str,
249 variant_index: u32,
250 _variant: &'static str,
251 len: usize,
252 ) -> Result<Self::SerializeTupleVariant, Self::Error> {
253 self.digest.update(&variant_index.to_be_bytes());
254 self.digest
255 .update(&try_into_sequence_length(len)?.to_be_bytes());
256 Ok(self)
257 }
258
259 fn serialize_map(self, len: Option<usize>) -> Result<Self::SerializeMap, Self::Error> {
260 let len = len.ok_or(Error::UndefinedSequenceLength)?;
261 self.digest
262 .update(&try_into_sequence_length(len)?.to_be_bytes());
263 Ok(self)
264 }
265
266 fn serialize_struct(
267 self,
268 _name: &'static str,
269 len: usize,
270 ) -> Result<Self::SerializeStruct, Self::Error> {
271 self.digest
272 .update(&try_into_sequence_length(len)?.to_be_bytes());
273 Ok(self)
274 }
275
276 fn serialize_struct_variant(
277 self,
278 _name: &'static str,
279 variant_index: u32,
280 _variant: &'static str,
281 len: usize,
282 ) -> Result<Self::SerializeStructVariant, Self::Error> {
283 self.digest.update(&variant_index.to_be_bytes());
284 self.digest
285 .update(&try_into_sequence_length(len)?.to_be_bytes());
286 Ok(self)
287 }
288
289 #[cfg(not(feature = "alloc"))]
290 fn collect_str<V: fmt::Display + ?Sized>(self, _: &V) -> Result<Self::Ok, Self::Error> {
291 Err(Error::CannotCollectStr)
292 }
293
294 fn is_human_readable(&self) -> bool {
295 false
296 }
297}
298
299impl<'a, T: Update> SerializeSeq for HashingSerializer<'a, T> {
300 type Ok = ();
301 type Error = Error;
302
303 fn serialize_element<V: ?Sized + Serialize>(&mut self, value: &V) -> Result<Self::Ok, Error> {
304 value.serialize(HashingSerializer {
305 digest: self.digest,
306 })?;
307 Ok(())
308 }
309
310 fn end(self) -> Result<Self::Ok, Error> {
311 Ok(())
312 }
313}
314
315impl<'a, T: Update> SerializeTuple for HashingSerializer<'a, T> {
316 type Ok = ();
317 type Error = Error;
318
319 fn serialize_element<V: ?Sized + Serialize>(&mut self, value: &V) -> Result<Self::Ok, Error> {
320 value.serialize(HashingSerializer {
321 digest: self.digest,
322 })?;
323 Ok(())
324 }
325
326 fn end(self) -> Result<Self::Ok, Error> {
327 Ok(())
328 }
329}
330
331impl<'a, T: Update> SerializeTupleStruct for HashingSerializer<'a, T> {
332 type Ok = ();
333 type Error = Error;
334
335 fn serialize_field<V: ?Sized + Serialize>(&mut self, value: &V) -> Result<Self::Ok, Error> {
336 value.serialize(HashingSerializer {
337 digest: self.digest,
338 })?;
339 Ok(())
340 }
341
342 fn end(self) -> Result<Self::Ok, Error> {
343 Ok(())
344 }
345}
346
347impl<'a, T: Update> SerializeTupleVariant for HashingSerializer<'a, T> {
348 type Ok = ();
349 type Error = Error;
350
351 fn serialize_field<V: ?Sized + Serialize>(&mut self, value: &V) -> Result<Self::Ok, Error> {
352 value.serialize(HashingSerializer {
353 digest: self.digest,
354 })?;
355 Ok(())
356 }
357
358 fn end(self) -> Result<Self::Ok, Error> {
359 Ok(())
360 }
361}
362
363impl<'a, T: Update> SerializeMap for HashingSerializer<'a, T> {
364 type Ok = ();
365 type Error = Error;
366
367 fn serialize_key<K: ?Sized + Serialize>(&mut self, key: &K) -> Result<Self::Ok, Error> {
368 key.serialize(HashingSerializer {
369 digest: self.digest,
370 })?;
371 Ok(())
372 }
373
374 fn serialize_value<V: ?Sized + Serialize>(&mut self, value: &V) -> Result<Self::Ok, Error> {
375 value.serialize(HashingSerializer {
376 digest: self.digest,
377 })?;
378 Ok(())
379 }
380
381 fn end(self) -> Result<Self::Ok, Error> {
382 Ok(())
383 }
384}
385
386impl<'a, T: Update> SerializeStruct for HashingSerializer<'a, T> {
387 type Ok = ();
388 type Error = Error;
389
390 fn serialize_field<V: ?Sized + Serialize>(
391 &mut self,
392 _key: &'static str,
393 value: &V,
394 ) -> Result<Self::Ok, Error> {
395 value.serialize(HashingSerializer {
396 digest: self.digest,
397 })?;
398 Ok(())
399 }
400
401 fn end(self) -> Result<Self::Ok, Error> {
402 Ok(())
403 }
404}
405
406impl<'a, T: Update> SerializeStructVariant for HashingSerializer<'a, T> {
407 type Ok = ();
408 type Error = Error;
409
410 fn serialize_field<V: ?Sized + Serialize>(
411 &mut self,
412 _key: &'static str,
413 value: &V,
414 ) -> Result<Self::Ok, Error> {
415 value.serialize(HashingSerializer {
416 digest: self.digest,
417 })?;
418 Ok(())
419 }
420
421 fn end(self) -> Result<Self::Ok, Error> {
422 Ok(())
423 }
424}
425
426#[cfg(test)]
427#[allow(clippy::unwrap_used)]
428mod tests {
429 use digest::Digest;
430 use k256::ecdsa::SigningKey;
431 use rand_core::OsRng;
432 use serde::Serialize;
433 use sha2::Sha256;
434
435 use super::HashingSerializer;
436
437 #[test]
438 fn hash_serializable() {
439 let sk = SigningKey::random(&mut OsRng);
440 let vk = sk.verifying_key();
441
442 let mut digest = Sha256::new();
443 let serializer = HashingSerializer {
444 digest: &mut digest,
445 };
446 vk.serialize(serializer).unwrap();
447 }
448}