Skip to main content

borsh/ser/
mod.rs

1use core::convert::TryFrom;
2use core::marker::PhantomData;
3
4use crate::__private::maybestd::{
5    borrow::{Cow, ToOwned},
6    boxed::Box,
7    collections::{BTreeMap, BTreeSet, LinkedList, VecDeque},
8    string::String,
9    vec::Vec,
10};
11use crate::error::check_zst;
12use crate::io::{Error, ErrorKind, Result, Write};
13
14pub(crate) mod helpers;
15
16const FLOAT_NAN_ERR: &str = "For portability reasons we do not allow to serialize NaNs.";
17
18/// A data-structure that can be serialized into binary format by NBOR.
19///
20/// ```
21/// use borsh::BorshSerialize;
22///
23/// /// derive is only available if borsh is built with `features = ["derive"]`
24/// # #[cfg(feature = "derive")]
25/// #[derive(BorshSerialize)]
26/// struct MyBorshSerializableStruct {
27///     value: String,
28/// }
29///
30///
31/// # #[cfg(feature = "derive")]
32/// let x = MyBorshSerializableStruct { value: "hello".to_owned() };
33/// let mut buffer: Vec<u8> = Vec::new();
34/// # #[cfg(feature = "derive")]
35/// x.serialize(&mut buffer).unwrap();
36/// # #[cfg(feature = "derive")]
37/// let single_serialized_buffer_len = buffer.len();
38///
39/// # #[cfg(feature = "derive")]
40/// x.serialize(&mut buffer).unwrap();
41/// # #[cfg(feature = "derive")]
42/// assert_eq!(buffer.len(), single_serialized_buffer_len * 2);
43///
44/// # #[cfg(feature = "derive")]
45/// let mut buffer: Vec<u8> = vec![0; 1024 + single_serialized_buffer_len];
46/// # #[cfg(feature = "derive")]
47/// let mut buffer_slice_enough_for_the_data = &mut buffer[1024..1024 + single_serialized_buffer_len];
48/// # #[cfg(feature = "derive")]
49/// x.serialize(&mut buffer_slice_enough_for_the_data).unwrap();
50/// ```
51pub trait BorshSerialize {
52    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()>;
53
54    #[inline]
55    #[doc(hidden)]
56    fn u8_slice(slice: &[Self]) -> Option<&[u8]>
57    where
58        Self: Sized,
59    {
60        let _ = slice;
61        None
62    }
63}
64
65impl BorshSerialize for u8 {
66    #[inline]
67    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
68        writer.write_all(core::slice::from_ref(self))
69    }
70
71    #[inline]
72    fn u8_slice(slice: &[Self]) -> Option<&[u8]> {
73        Some(slice)
74    }
75}
76
77macro_rules! impl_for_integer {
78    ($type: ident) => {
79        impl BorshSerialize for $type {
80            #[inline]
81            fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
82                let bytes = self.to_le_bytes();
83                writer.write_all(&bytes)
84            }
85        }
86    };
87}
88
89impl_for_integer!(i8);
90impl_for_integer!(i16);
91impl_for_integer!(i32);
92impl_for_integer!(i64);
93impl_for_integer!(i128);
94impl_for_integer!(u16);
95impl_for_integer!(u32);
96impl_for_integer!(u64);
97impl_for_integer!(u128);
98
99macro_rules! impl_for_nonzero_integer {
100    ($type: ty) => {
101        impl BorshSerialize for $type {
102            #[inline]
103            fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
104                BorshSerialize::serialize(&self.get(), writer)
105            }
106        }
107    };
108}
109
110impl_for_nonzero_integer!(core::num::NonZeroI8);
111impl_for_nonzero_integer!(core::num::NonZeroI16);
112impl_for_nonzero_integer!(core::num::NonZeroI32);
113impl_for_nonzero_integer!(core::num::NonZeroI64);
114impl_for_nonzero_integer!(core::num::NonZeroI128);
115impl_for_nonzero_integer!(core::num::NonZeroU8);
116impl_for_nonzero_integer!(core::num::NonZeroU16);
117impl_for_nonzero_integer!(core::num::NonZeroU32);
118impl_for_nonzero_integer!(core::num::NonZeroU64);
119impl_for_nonzero_integer!(core::num::NonZeroU128);
120impl_for_nonzero_integer!(core::num::NonZeroUsize);
121
122impl BorshSerialize for isize {
123    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
124        BorshSerialize::serialize(&(*self as i64), writer)
125    }
126}
127
128impl BorshSerialize for usize {
129    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
130        BorshSerialize::serialize(&(*self as u64), writer)
131    }
132}
133
134// Note NaNs have a portability issue. Specifically, signalling NaNs on MIPS are quiet NaNs on x86,
135// and vice-versa. We disallow NaNs to avoid this issue.
136macro_rules! impl_for_float {
137    ($type: ident) => {
138        impl BorshSerialize for $type {
139            #[inline]
140            fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
141                if self.is_nan() {
142                    return Err(Error::new(ErrorKind::InvalidData, FLOAT_NAN_ERR));
143                }
144                writer.write_all(&self.to_bits().to_le_bytes())
145            }
146        }
147    };
148}
149
150impl_for_float!(f32);
151impl_for_float!(f64);
152
153impl BorshSerialize for bool {
154    #[inline]
155    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
156        (u8::from(*self)).serialize(writer)
157    }
158}
159
160impl<T> BorshSerialize for Option<T>
161where
162    T: BorshSerialize,
163{
164    #[inline]
165    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
166        match self {
167            None => 0u8.serialize(writer),
168            Some(value) => {
169                1u8.serialize(writer)?;
170                value.serialize(writer)
171            }
172        }
173    }
174}
175
176impl<T, E> BorshSerialize for core::result::Result<T, E>
177where
178    T: BorshSerialize,
179    E: BorshSerialize,
180{
181    #[inline]
182    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
183        match self {
184            Err(e) => {
185                0u8.serialize(writer)?;
186                e.serialize(writer)
187            }
188            Ok(v) => {
189                1u8.serialize(writer)?;
190                v.serialize(writer)
191            }
192        }
193    }
194}
195
196impl BorshSerialize for str {
197    #[inline]
198    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
199        self.as_bytes().serialize(writer)
200    }
201}
202
203impl BorshSerialize for String {
204    #[inline]
205    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
206        self.as_bytes().serialize(writer)
207    }
208}
209
210/// Module is available if borsh is built with `features = ["ascii"]`.
211#[cfg(feature = "ascii")]
212pub mod ascii {
213    //!
214    //! Module defines [BorshSerialize] implementation for
215    //! some types from [ascii](::ascii) crate.
216    use super::BorshSerialize;
217    use crate::io::{Result, Write};
218
219    impl BorshSerialize for ascii::AsciiChar {
220        #[inline]
221        fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
222            self.as_byte().serialize(writer)
223        }
224    }
225
226    impl BorshSerialize for ascii::AsciiStr {
227        #[inline]
228        fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
229            self.as_bytes().serialize(writer)
230        }
231    }
232
233    impl BorshSerialize for ascii::AsciiString {
234        #[inline]
235        fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
236            self.as_bytes().serialize(writer)
237        }
238    }
239}
240
241/// Helper method that is used to serialize a slice of data (without the length marker).
242#[inline]
243fn serialize_slice<T: BorshSerialize, W: Write>(data: &[T], writer: &mut W) -> Result<()> {
244    if let Some(u8_slice) = T::u8_slice(data) {
245        writer.write_all(u8_slice)?;
246    } else {
247        for item in data {
248            item.serialize(writer)?;
249        }
250    }
251    Ok(())
252}
253
254impl<T> BorshSerialize for [T]
255where
256    T: BorshSerialize,
257{
258    #[inline]
259    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
260        writer.write_all(
261            &(u32::try_from(self.len()).map_err(|_| ErrorKind::InvalidData)?).to_le_bytes(),
262        )?;
263        serialize_slice(self, writer)
264    }
265}
266
267impl<T: BorshSerialize + ?Sized> BorshSerialize for &T {
268    #[inline]
269    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
270        (*self).serialize(writer)
271    }
272}
273
274impl<T> BorshSerialize for Cow<'_, T>
275where
276    T: BorshSerialize + ToOwned + ?Sized,
277{
278    #[inline]
279    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
280        self.as_ref().serialize(writer)
281    }
282}
283
284impl<T> BorshSerialize for Vec<T>
285where
286    T: BorshSerialize,
287{
288    #[inline]
289    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
290        check_zst::<T>()?;
291
292        self.as_slice().serialize(writer)
293    }
294}
295
296#[cfg(feature = "bytes")]
297impl BorshSerialize for bytes::Bytes {
298    #[inline]
299    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
300        self.as_ref().serialize(writer)
301    }
302}
303
304#[cfg(feature = "bytes")]
305impl BorshSerialize for bytes::BytesMut {
306    #[inline]
307    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
308        self.as_ref().serialize(writer)
309    }
310}
311
312#[cfg(feature = "bson")]
313impl BorshSerialize for bson::oid::ObjectId {
314    #[inline]
315    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
316        self.bytes().serialize(writer)
317    }
318}
319
320#[cfg(feature = "indexmap")]
321// Taken from https://github.com/indexmap-rs/indexmap/blob/dd06e5773e4f91748396c67d00c83637f5c0dd49/src/borsh.rs#L74C1-L86C2
322// license: MIT OR Apache-2.0
323impl<T, S> BorshSerialize for indexmap::IndexSet<T, S>
324where
325    T: BorshSerialize,
326{
327    #[inline]
328    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
329        check_zst::<T>()?;
330
331        let iterator = self.iter();
332
333        u32::try_from(iterator.len())
334            .map_err(|_| ErrorKind::InvalidData)?
335            .serialize(writer)?;
336
337        for item in iterator {
338            item.serialize(writer)?;
339        }
340
341        Ok(())
342    }
343}
344
345#[cfg(feature = "indexmap")]
346// Taken from https://github.com/indexmap-rs/indexmap/blob/dd06e5773e4f91748396c67d00c83637f5c0dd49/src/borsh.rs#L15
347// license: MIT OR Apache-2.0
348impl<K, V, S> BorshSerialize for indexmap::IndexMap<K, V, S>
349where
350    K: BorshSerialize,
351    V: BorshSerialize,
352{
353    #[inline]
354    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
355        check_zst::<K>()?;
356
357        let iterator = self.iter();
358
359        u32::try_from(iterator.len())
360            .map_err(|_| ErrorKind::InvalidData)?
361            .serialize(writer)?;
362
363        for (key, value) in iterator {
364            key.serialize(writer)?;
365            value.serialize(writer)?;
366        }
367
368        Ok(())
369    }
370}
371
372#[cfg(feature = "uuid")]
373impl BorshSerialize for uuid::Uuid {
374    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
375        BorshSerialize::serialize(&self.as_bytes(), writer)?;
376
377        Ok(())
378    }
379}
380
381impl<T> BorshSerialize for VecDeque<T>
382where
383    T: BorshSerialize,
384{
385    #[inline]
386    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
387        check_zst::<T>()?;
388
389        writer.write_all(
390            &(u32::try_from(self.len()).map_err(|_| ErrorKind::InvalidData)?).to_le_bytes(),
391        )?;
392        let slices = self.as_slices();
393        serialize_slice(slices.0, writer)?;
394        serialize_slice(slices.1, writer)
395    }
396}
397
398impl<T> BorshSerialize for LinkedList<T>
399where
400    T: BorshSerialize,
401{
402    #[inline]
403    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
404        check_zst::<T>()?;
405
406        writer.write_all(
407            &(u32::try_from(self.len()).map_err(|_| ErrorKind::InvalidData)?).to_le_bytes(),
408        )?;
409        for item in self {
410            item.serialize(writer)?;
411        }
412        Ok(())
413    }
414}
415
416/// Module is available if borsh is built with `features = ["std"]` or `features = ["hashbrown"]`.
417///
418/// Module defines [BorshSerialize] implementation for
419/// [HashMap](std::collections::HashMap)/[HashSet](std::collections::HashSet).
420#[cfg(hash_collections)]
421pub mod hashes {
422    use crate::__private::maybestd::vec::Vec;
423    use crate::error::check_zst;
424    use crate::{
425        __private::maybestd::collections::{HashMap, HashSet},
426        BorshSerialize,
427    };
428    use core::convert::TryFrom;
429    use core::hash::BuildHasher;
430
431    use crate::io::{ErrorKind, Result, Write};
432
433    impl<K, V, H> BorshSerialize for HashMap<K, V, H>
434    where
435        K: BorshSerialize + Ord,
436        V: BorshSerialize,
437        H: BuildHasher,
438    {
439        #[inline]
440        fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
441            check_zst::<K>()?;
442
443            let mut vec = self.iter().collect::<Vec<_>>();
444            vec.sort_by_key(|(a, _)| *a);
445            u32::try_from(vec.len())
446                .map_err(|_| ErrorKind::InvalidData)?
447                .serialize(writer)?;
448            for kv in vec {
449                kv.serialize(writer)?;
450            }
451            Ok(())
452        }
453    }
454
455    impl<T, H> BorshSerialize for HashSet<T, H>
456    where
457        T: BorshSerialize + Ord,
458        H: BuildHasher,
459    {
460        #[inline]
461        fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
462            check_zst::<T>()?;
463
464            let mut vec = self.iter().collect::<Vec<_>>();
465            vec.sort();
466            u32::try_from(vec.len())
467                .map_err(|_| ErrorKind::InvalidData)?
468                .serialize(writer)?;
469            for item in vec {
470                item.serialize(writer)?;
471            }
472            Ok(())
473        }
474    }
475}
476
477impl<K, V> BorshSerialize for BTreeMap<K, V>
478where
479    K: BorshSerialize,
480    V: BorshSerialize,
481{
482    #[inline]
483    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
484        check_zst::<K>()?;
485        // NOTE: BTreeMap iterates over the entries that are sorted by key, so the serialization
486        // result will be consistent without a need to sort the entries as we do for HashMap
487        // serialization.
488        u32::try_from(self.len())
489            .map_err(|_| ErrorKind::InvalidData)?
490            .serialize(writer)?;
491        for (key, value) in self {
492            key.serialize(writer)?;
493            value.serialize(writer)?;
494        }
495        Ok(())
496    }
497}
498
499impl<T> BorshSerialize for BTreeSet<T>
500where
501    T: BorshSerialize,
502{
503    #[inline]
504    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
505        check_zst::<T>()?;
506        // NOTE: BTreeSet iterates over the items that are sorted, so the serialization result will
507        // be consistent without a need to sort the entries as we do for HashSet serialization.
508        u32::try_from(self.len())
509            .map_err(|_| ErrorKind::InvalidData)?
510            .serialize(writer)?;
511        for item in self {
512            item.serialize(writer)?;
513        }
514        Ok(())
515    }
516}
517
518impl BorshSerialize for core::net::SocketAddr {
519    #[inline]
520    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
521        match *self {
522            core::net::SocketAddr::V4(ref addr) => {
523                0u8.serialize(writer)?;
524                addr.serialize(writer)
525            }
526            core::net::SocketAddr::V6(ref addr) => {
527                1u8.serialize(writer)?;
528                addr.serialize(writer)
529            }
530        }
531    }
532}
533
534impl BorshSerialize for core::net::SocketAddrV4 {
535    #[inline]
536    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
537        self.ip().serialize(writer)?;
538        self.port().serialize(writer)
539    }
540}
541
542impl BorshSerialize for core::net::SocketAddrV6 {
543    #[inline]
544    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
545        self.ip().serialize(writer)?;
546        self.port().serialize(writer)
547    }
548}
549
550impl BorshSerialize for core::net::Ipv4Addr {
551    #[inline]
552    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
553        writer.write_all(&self.octets())
554    }
555}
556
557impl BorshSerialize for core::net::Ipv6Addr {
558    #[inline]
559    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
560        writer.write_all(&self.octets())
561    }
562}
563
564impl BorshSerialize for core::net::IpAddr {
565    #[inline]
566    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
567        match self {
568            core::net::IpAddr::V4(ipv4) => {
569                writer.write_all(&0u8.to_le_bytes())?;
570                ipv4.serialize(writer)
571            }
572            core::net::IpAddr::V6(ipv6) => {
573                writer.write_all(&1u8.to_le_bytes())?;
574                ipv6.serialize(writer)
575            }
576        }
577    }
578}
579impl<T: BorshSerialize + ?Sized> BorshSerialize for Box<T> {
580    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
581        self.as_ref().serialize(writer)
582    }
583}
584
585impl<T, const N: usize> BorshSerialize for [T; N]
586where
587    T: BorshSerialize,
588{
589    #[inline]
590    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
591        if N == 0 {
592            return Ok(());
593        } else if let Some(u8_slice) = T::u8_slice(self) {
594            writer.write_all(u8_slice)?;
595        } else {
596            for el in self.iter() {
597                el.serialize(writer)?;
598            }
599        }
600        Ok(())
601    }
602}
603
604macro_rules! impl_tuple {
605    (@unit $name:ty) => {
606        impl BorshSerialize for $name {
607            #[inline]
608            fn serialize<W: Write>(&self, _writer: &mut W) -> Result<()> {
609                Ok(())
610            }
611        }
612    };
613
614    ($($idx:tt $name:ident)+) => {
615      impl<$($name),+> BorshSerialize for ($($name,)+)
616      where $($name: BorshSerialize,)+
617      {
618        #[inline]
619        fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
620            $(self.$idx.serialize(writer)?;)+
621            Ok(())
622        }
623      }
624    };
625}
626
627impl_tuple!(@unit ());
628impl_tuple!(@unit core::ops::RangeFull);
629
630impl_tuple!(0 T0);
631impl_tuple!(0 T0 1 T1);
632impl_tuple!(0 T0 1 T1 2 T2);
633impl_tuple!(0 T0 1 T1 2 T2 3 T3);
634impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4);
635impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5);
636impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6);
637impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7);
638impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8);
639impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8 9 T9);
640impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8 9 T9 10 T10);
641impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8 9 T9 10 T10 11 T11);
642impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8 9 T9 10 T10 11 T11 12 T12);
643impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8 9 T9 10 T10 11 T11 12 T12 13 T13);
644impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8 9 T9 10 T10 11 T11 12 T12 13 T13 14 T14);
645impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8 9 T9 10 T10 11 T11 12 T12 13 T13 14 T14 15 T15);
646impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8 9 T9 10 T10 11 T11 12 T12 13 T13 14 T14 15 T15 16 T16);
647impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8 9 T9 10 T10 11 T11 12 T12 13 T13 14 T14 15 T15 16 T16 17 T17);
648impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8 9 T9 10 T10 11 T11 12 T12 13 T13 14 T14 15 T15 16 T16 17 T17 18 T18);
649impl_tuple!(0 T0 1 T1 2 T2 3 T3 4 T4 5 T5 6 T6 7 T7 8 T8 9 T9 10 T10 11 T11 12 T12 13 T13 14 T14 15 T15 16 T16 17 T17 18 T18 19 T19);
650
651macro_rules! impl_range {
652    ($type:ident, $this:ident, $($field:expr),*) => {
653        impl<T: BorshSerialize> BorshSerialize for core::ops::$type<T> {
654            #[inline]
655            fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
656                let $this = self;
657                $( $field.serialize(writer)?; )*
658                Ok(())
659            }
660        }
661    };
662}
663
664impl_range!(Range, this, &this.start, &this.end);
665impl_range!(RangeInclusive, this, this.start(), this.end());
666impl_range!(RangeFrom, this, &this.start);
667impl_range!(RangeTo, this, &this.end);
668impl_range!(RangeToInclusive, this, &this.end);
669
670/// Module is available if borsh is built with `features = ["rc"]`.
671#[cfg(feature = "rc")]
672pub mod rc {
673    //!
674    //! Module defines [BorshSerialize] implementation for
675    //! [alloc::rc::Rc](std::rc::Rc) and [alloc::sync::Arc](std::sync::Arc).
676    use crate::__private::maybestd::{rc::Rc, sync::Arc};
677    use crate::io::{Result, Write};
678    use crate::BorshSerialize;
679
680    /// This impl requires the [`"rc"`] Cargo feature of borsh.
681    ///
682    /// Serializing a data structure containing `Rc` will serialize a copy of
683    /// the contents of the `Rc` each time the `Rc` is referenced within the
684    /// data structure. Serialization will not attempt to deduplicate these
685    /// repeated data.
686    impl<T: BorshSerialize + ?Sized> BorshSerialize for Rc<T> {
687        fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
688            (**self).serialize(writer)
689        }
690    }
691
692    /// This impl requires the [`"rc"`] Cargo feature of borsh.
693    ///
694    /// Serializing a data structure containing `Arc` will serialize a copy of
695    /// the contents of the `Arc` each time the `Arc` is referenced within the
696    /// data structure. Serialization will not attempt to deduplicate these
697    /// repeated data.
698    impl<T: BorshSerialize + ?Sized> BorshSerialize for Arc<T> {
699        fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
700            (**self).serialize(writer)
701        }
702    }
703}
704
705impl<T: ?Sized> BorshSerialize for PhantomData<T> {
706    fn serialize<W: Write>(&self, _: &mut W) -> Result<()> {
707        Ok(())
708    }
709}
710
711impl<T> BorshSerialize for core::cell::Cell<T>
712where
713    T: BorshSerialize + Copy,
714{
715    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
716        <T as BorshSerialize>::serialize(&self.get(), writer)
717    }
718}
719
720impl<T> BorshSerialize for core::cell::RefCell<T>
721where
722    T: BorshSerialize + Sized,
723{
724    fn serialize<W: Write>(&self, writer: &mut W) -> Result<()> {
725        match self.try_borrow() {
726            Ok(ref value) => value.serialize(writer),
727            Err(_) => Err(Error::other("already mutably borrowed")),
728        }
729    }
730}