mirror of https://git.sr.ht/~stygianentity/bincode
Added support for atomic integers
This commit is contained in:
parent
8ab730eb87
commit
1f261cede3
|
|
@ -23,9 +23,10 @@ description = "A binary serialization / deserialization strategy for transformin
|
|||
edition = "2018"
|
||||
|
||||
[features]
|
||||
default = ["std", "derive"]
|
||||
default = ["std", "derive", "atomic"]
|
||||
std = ["alloc"]
|
||||
alloc = []
|
||||
atomic = []
|
||||
derive = ["bincode_derive"]
|
||||
|
||||
[dependencies]
|
||||
|
|
|
|||
|
|
@ -0,0 +1,137 @@
|
|||
use crate::{de::Decodable, enc::Encodeable};
|
||||
use core::sync::atomic::{
|
||||
AtomicBool, AtomicI16, AtomicI32, AtomicI64, AtomicI8, AtomicIsize, AtomicU16, AtomicU32,
|
||||
AtomicU64, AtomicU8, AtomicUsize, Ordering,
|
||||
};
|
||||
|
||||
impl Encodeable for AtomicBool {
|
||||
fn encode<E: crate::enc::Encode>(&self, encoder: E) -> Result<(), crate::error::EncodeError> {
|
||||
self.load(Ordering::SeqCst).encode(encoder)
|
||||
}
|
||||
}
|
||||
|
||||
impl Decodable for AtomicBool {
|
||||
fn decode<D: crate::de::Decode>(decoder: D) -> Result<Self, crate::error::DecodeError> {
|
||||
Ok(AtomicBool::new(Decodable::decode(decoder)?))
|
||||
}
|
||||
}
|
||||
|
||||
impl Encodeable for AtomicU8 {
|
||||
fn encode<E: crate::enc::Encode>(&self, encoder: E) -> Result<(), crate::error::EncodeError> {
|
||||
self.load(Ordering::SeqCst).encode(encoder)
|
||||
}
|
||||
}
|
||||
|
||||
impl Decodable for AtomicU8 {
|
||||
fn decode<D: crate::de::Decode>(decoder: D) -> Result<Self, crate::error::DecodeError> {
|
||||
Ok(AtomicU8::new(Decodable::decode(decoder)?))
|
||||
}
|
||||
}
|
||||
|
||||
impl Encodeable for AtomicU16 {
|
||||
fn encode<E: crate::enc::Encode>(&self, encoder: E) -> Result<(), crate::error::EncodeError> {
|
||||
self.load(Ordering::SeqCst).encode(encoder)
|
||||
}
|
||||
}
|
||||
|
||||
impl Decodable for AtomicU16 {
|
||||
fn decode<D: crate::de::Decode>(decoder: D) -> Result<Self, crate::error::DecodeError> {
|
||||
Ok(AtomicU16::new(Decodable::decode(decoder)?))
|
||||
}
|
||||
}
|
||||
|
||||
impl Encodeable for AtomicU32 {
|
||||
fn encode<E: crate::enc::Encode>(&self, encoder: E) -> Result<(), crate::error::EncodeError> {
|
||||
self.load(Ordering::SeqCst).encode(encoder)
|
||||
}
|
||||
}
|
||||
|
||||
impl Decodable for AtomicU32 {
|
||||
fn decode<D: crate::de::Decode>(decoder: D) -> Result<Self, crate::error::DecodeError> {
|
||||
Ok(AtomicU32::new(Decodable::decode(decoder)?))
|
||||
}
|
||||
}
|
||||
|
||||
impl Encodeable for AtomicU64 {
|
||||
fn encode<E: crate::enc::Encode>(&self, encoder: E) -> Result<(), crate::error::EncodeError> {
|
||||
self.load(Ordering::SeqCst).encode(encoder)
|
||||
}
|
||||
}
|
||||
|
||||
impl Decodable for AtomicU64 {
|
||||
fn decode<D: crate::de::Decode>(decoder: D) -> Result<Self, crate::error::DecodeError> {
|
||||
Ok(AtomicU64::new(Decodable::decode(decoder)?))
|
||||
}
|
||||
}
|
||||
|
||||
impl Encodeable for AtomicUsize {
|
||||
fn encode<E: crate::enc::Encode>(&self, encoder: E) -> Result<(), crate::error::EncodeError> {
|
||||
self.load(Ordering::SeqCst).encode(encoder)
|
||||
}
|
||||
}
|
||||
|
||||
impl Decodable for AtomicUsize {
|
||||
fn decode<D: crate::de::Decode>(decoder: D) -> Result<Self, crate::error::DecodeError> {
|
||||
Ok(AtomicUsize::new(Decodable::decode(decoder)?))
|
||||
}
|
||||
}
|
||||
|
||||
impl Encodeable for AtomicI8 {
|
||||
fn encode<E: crate::enc::Encode>(&self, encoder: E) -> Result<(), crate::error::EncodeError> {
|
||||
self.load(Ordering::SeqCst).encode(encoder)
|
||||
}
|
||||
}
|
||||
|
||||
impl Decodable for AtomicI8 {
|
||||
fn decode<D: crate::de::Decode>(decoder: D) -> Result<Self, crate::error::DecodeError> {
|
||||
Ok(AtomicI8::new(Decodable::decode(decoder)?))
|
||||
}
|
||||
}
|
||||
|
||||
impl Encodeable for AtomicI16 {
|
||||
fn encode<E: crate::enc::Encode>(&self, encoder: E) -> Result<(), crate::error::EncodeError> {
|
||||
self.load(Ordering::SeqCst).encode(encoder)
|
||||
}
|
||||
}
|
||||
|
||||
impl Decodable for AtomicI16 {
|
||||
fn decode<D: crate::de::Decode>(decoder: D) -> Result<Self, crate::error::DecodeError> {
|
||||
Ok(AtomicI16::new(Decodable::decode(decoder)?))
|
||||
}
|
||||
}
|
||||
|
||||
impl Encodeable for AtomicI32 {
|
||||
fn encode<E: crate::enc::Encode>(&self, encoder: E) -> Result<(), crate::error::EncodeError> {
|
||||
self.load(Ordering::SeqCst).encode(encoder)
|
||||
}
|
||||
}
|
||||
|
||||
impl Decodable for AtomicI32 {
|
||||
fn decode<D: crate::de::Decode>(decoder: D) -> Result<Self, crate::error::DecodeError> {
|
||||
Ok(AtomicI32::new(Decodable::decode(decoder)?))
|
||||
}
|
||||
}
|
||||
|
||||
impl Encodeable for AtomicI64 {
|
||||
fn encode<E: crate::enc::Encode>(&self, encoder: E) -> Result<(), crate::error::EncodeError> {
|
||||
self.load(Ordering::SeqCst).encode(encoder)
|
||||
}
|
||||
}
|
||||
|
||||
impl Decodable for AtomicI64 {
|
||||
fn decode<D: crate::de::Decode>(decoder: D) -> Result<Self, crate::error::DecodeError> {
|
||||
Ok(AtomicI64::new(Decodable::decode(decoder)?))
|
||||
}
|
||||
}
|
||||
|
||||
impl Encodeable for AtomicIsize {
|
||||
fn encode<E: crate::enc::Encode>(&self, encoder: E) -> Result<(), crate::error::EncodeError> {
|
||||
self.load(Ordering::SeqCst).encode(encoder)
|
||||
}
|
||||
}
|
||||
|
||||
impl Decodable for AtomicIsize {
|
||||
fn decode<D: crate::de::Decode>(decoder: D) -> Result<Self, crate::error::DecodeError> {
|
||||
Ok(AtomicIsize::new(Decodable::decode(decoder)?))
|
||||
}
|
||||
}
|
||||
|
|
@ -1,3 +1,8 @@
|
|||
#[cfg(feature = "atomic")]
|
||||
mod atomic;
|
||||
#[cfg(feature = "atomic")]
|
||||
pub use self::atomic::*;
|
||||
|
||||
#[cfg(feature = "alloc")]
|
||||
mod impl_alloc;
|
||||
#[cfg(feature = "alloc")]
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@ use alloc::borrow::Cow;
|
|||
use alloc::collections::*;
|
||||
use alloc::rc::Rc;
|
||||
use alloc::sync::Arc;
|
||||
use utils::the_same;
|
||||
use utils::{the_same, the_same_with_comparer};
|
||||
|
||||
struct Foo {
|
||||
pub a: u32,
|
||||
|
|
@ -55,6 +55,18 @@ fn test_alloc_commons() {
|
|||
the_same(Cow::<u32>::Borrowed(&5));
|
||||
the_same(Rc::<u32>::new(5));
|
||||
the_same(Arc::<u32>::new(5));
|
||||
the_same_with_comparer(
|
||||
{
|
||||
let mut map = BinaryHeap::<u32>::new();
|
||||
map.push(1);
|
||||
map.push(2);
|
||||
map.push(3);
|
||||
map.push(4);
|
||||
map.push(5);
|
||||
map
|
||||
},
|
||||
|a, b| a.into_iter().collect::<Vec<_>>() == b.into_iter().collect::<Vec<_>>(),
|
||||
);
|
||||
the_same({
|
||||
let mut map = BTreeMap::<u32, i32>::new();
|
||||
map.insert(5, -5);
|
||||
|
|
|
|||
|
|
@ -0,0 +1,49 @@
|
|||
#![cfg(feature = "atomic")]
|
||||
|
||||
mod utils;
|
||||
|
||||
use core::sync::atomic::{
|
||||
AtomicBool, AtomicI16, AtomicI32, AtomicI64, AtomicI8, AtomicIsize, AtomicU16, AtomicU32,
|
||||
AtomicU64, AtomicU8, AtomicUsize, Ordering,
|
||||
};
|
||||
use utils::the_same_with_comparer;
|
||||
|
||||
#[test]
|
||||
fn test_atomic_commons() {
|
||||
the_same_with_comparer(AtomicBool::new(true), |a, b| {
|
||||
a.load(Ordering::SeqCst) == b.load(Ordering::SeqCst)
|
||||
});
|
||||
the_same_with_comparer(AtomicBool::new(false), |a, b| {
|
||||
a.load(Ordering::SeqCst) == b.load(Ordering::SeqCst)
|
||||
});
|
||||
the_same_with_comparer(AtomicU8::new(0), |a, b| {
|
||||
a.load(Ordering::SeqCst) == b.load(Ordering::SeqCst)
|
||||
});
|
||||
the_same_with_comparer(AtomicU16::new(0), |a, b| {
|
||||
a.load(Ordering::SeqCst) == b.load(Ordering::SeqCst)
|
||||
});
|
||||
the_same_with_comparer(AtomicU32::new(0), |a, b| {
|
||||
a.load(Ordering::SeqCst) == b.load(Ordering::SeqCst)
|
||||
});
|
||||
the_same_with_comparer(AtomicU64::new(0), |a, b| {
|
||||
a.load(Ordering::SeqCst) == b.load(Ordering::SeqCst)
|
||||
});
|
||||
the_same_with_comparer(AtomicUsize::new(0), |a, b| {
|
||||
a.load(Ordering::SeqCst) == b.load(Ordering::SeqCst)
|
||||
});
|
||||
the_same_with_comparer(AtomicI8::new(0), |a, b| {
|
||||
a.load(Ordering::SeqCst) == b.load(Ordering::SeqCst)
|
||||
});
|
||||
the_same_with_comparer(AtomicI16::new(0), |a, b| {
|
||||
a.load(Ordering::SeqCst) == b.load(Ordering::SeqCst)
|
||||
});
|
||||
the_same_with_comparer(AtomicI32::new(0), |a, b| {
|
||||
a.load(Ordering::SeqCst) == b.load(Ordering::SeqCst)
|
||||
});
|
||||
the_same_with_comparer(AtomicI64::new(0), |a, b| {
|
||||
a.load(Ordering::SeqCst) == b.load(Ordering::SeqCst)
|
||||
});
|
||||
the_same_with_comparer(AtomicIsize::new(0), |a, b| {
|
||||
a.load(Ordering::SeqCst) == b.load(Ordering::SeqCst)
|
||||
});
|
||||
}
|
||||
21
tests/std.rs
21
tests/std.rs
|
|
@ -11,6 +11,8 @@ use std::{
|
|||
};
|
||||
use utils::the_same;
|
||||
|
||||
use crate::utils::the_same_with_comparer;
|
||||
|
||||
struct Foo {
|
||||
pub a: u32,
|
||||
pub b: u32,
|
||||
|
|
@ -79,7 +81,14 @@ fn test_std_commons() {
|
|||
0,
|
||||
0,
|
||||
)));
|
||||
the_same_with_comparer(Mutex::new("Hello world".to_string()), |a, b| {
|
||||
&*a.lock().unwrap() == &*b.lock().unwrap()
|
||||
});
|
||||
the_same_with_comparer(RwLock::new("Hello world".to_string()), |a, b| {
|
||||
&*a.read().unwrap() == &*b.read().unwrap()
|
||||
});
|
||||
|
||||
// Borrowed values
|
||||
let config = bincode::config::Default;
|
||||
let mut buffer = [0u8; 1024];
|
||||
|
||||
|
|
@ -89,18 +98,6 @@ fn test_std_commons() {
|
|||
let decoded: &CStr = bincode::decode_with_config(&mut buffer[..len], config).unwrap();
|
||||
assert_eq!(cstr, decoded);
|
||||
|
||||
// Mutex<T>
|
||||
let mutex = Mutex::new("Hello world".to_string());
|
||||
let len = bincode::encode_into_slice_with_config(&mutex, &mut buffer, config).unwrap();
|
||||
let decoded: Mutex<String> = bincode::decode_with_config(&mut buffer[..len], config).unwrap();
|
||||
assert_eq!(&*mutex.lock().unwrap(), &*decoded.lock().unwrap());
|
||||
|
||||
// RwLock<T>
|
||||
let rwlock = RwLock::new("Hello world".to_string());
|
||||
let len = bincode::encode_into_slice_with_config(&rwlock, &mut buffer, config).unwrap();
|
||||
let decoded: RwLock<String> = bincode::decode_with_config(&mut buffer[..len], config).unwrap();
|
||||
assert_eq!(&*rwlock.read().unwrap(), &*decoded.read().unwrap());
|
||||
|
||||
// Path
|
||||
let path = Path::new("C:/Program Files/Foo");
|
||||
let len = bincode::encode_into_slice_with_config(path, &mut buffer, config).unwrap();
|
||||
|
|
|
|||
|
|
@ -1,13 +1,14 @@
|
|||
use bincode::config::{self, Config};
|
||||
use core::fmt::Debug;
|
||||
|
||||
fn the_same_with_config<V, C>(element: V, config: C)
|
||||
fn the_same_with_config<V, C, CMP>(element: &V, config: C, cmp: CMP)
|
||||
where
|
||||
V: bincode::enc::Encodeable + bincode::de::Decodable + PartialEq + Debug + Clone + 'static,
|
||||
V: bincode::enc::Encodeable + bincode::de::Decodable + Debug + 'static,
|
||||
C: Config,
|
||||
CMP: Fn(&V, &V) -> bool,
|
||||
{
|
||||
let mut buffer = [0u8; 1024];
|
||||
let len = bincode::encode_into_slice_with_config(element.clone(), &mut buffer, config).unwrap();
|
||||
let len = bincode::encode_into_slice_with_config(&element, &mut buffer, config).unwrap();
|
||||
println!(
|
||||
"{:?}: {:?} ({:?})",
|
||||
element,
|
||||
|
|
@ -16,68 +17,91 @@ where
|
|||
);
|
||||
let decoded: V = bincode::decode_with_config(&mut buffer, config).unwrap();
|
||||
|
||||
assert_eq!(element, decoded);
|
||||
assert!(
|
||||
cmp(&element, &decoded),
|
||||
"Comparison failed\nDecoded: {:?}\nExpected: {:?}\nBytes: {:?}",
|
||||
decoded,
|
||||
element,
|
||||
&buffer[..len],
|
||||
);
|
||||
}
|
||||
|
||||
pub fn the_same<V>(element: V)
|
||||
pub fn the_same_with_comparer<V, CMP>(element: V, cmp: CMP)
|
||||
where
|
||||
V: bincode::enc::Encodeable + bincode::de::Decodable + PartialEq + Debug + Clone + 'static,
|
||||
V: bincode::enc::Encodeable + bincode::de::Decodable + Debug + 'static,
|
||||
CMP: Fn(&V, &V) -> bool,
|
||||
{
|
||||
// A matrix of each different config option possible
|
||||
the_same_with_config(
|
||||
element.clone(),
|
||||
&element,
|
||||
config::Default
|
||||
.with_little_endian()
|
||||
.with_fixed_int_encoding()
|
||||
.skip_fixed_array_length(),
|
||||
&cmp,
|
||||
);
|
||||
the_same_with_config(
|
||||
element.clone(),
|
||||
&element,
|
||||
config::Default
|
||||
.with_big_endian()
|
||||
.with_fixed_int_encoding()
|
||||
.skip_fixed_array_length(),
|
||||
&cmp,
|
||||
);
|
||||
the_same_with_config(
|
||||
element.clone(),
|
||||
&element,
|
||||
config::Default
|
||||
.with_little_endian()
|
||||
.with_variable_int_encoding()
|
||||
.skip_fixed_array_length(),
|
||||
&cmp,
|
||||
);
|
||||
the_same_with_config(
|
||||
element.clone(),
|
||||
&element,
|
||||
config::Default
|
||||
.with_big_endian()
|
||||
.with_variable_int_encoding()
|
||||
.skip_fixed_array_length(),
|
||||
&cmp,
|
||||
);
|
||||
the_same_with_config(
|
||||
element.clone(),
|
||||
&element,
|
||||
config::Default
|
||||
.with_little_endian()
|
||||
.with_fixed_int_encoding()
|
||||
.write_fixed_array_length(),
|
||||
&cmp,
|
||||
);
|
||||
the_same_with_config(
|
||||
element.clone(),
|
||||
&element,
|
||||
config::Default
|
||||
.with_big_endian()
|
||||
.with_fixed_int_encoding()
|
||||
.write_fixed_array_length(),
|
||||
&cmp,
|
||||
);
|
||||
the_same_with_config(
|
||||
element.clone(),
|
||||
&element,
|
||||
config::Default
|
||||
.with_little_endian()
|
||||
.with_variable_int_encoding()
|
||||
.write_fixed_array_length(),
|
||||
&cmp,
|
||||
);
|
||||
the_same_with_config(
|
||||
element,
|
||||
&element,
|
||||
config::Default
|
||||
.with_big_endian()
|
||||
.with_variable_int_encoding()
|
||||
.write_fixed_array_length(),
|
||||
&cmp,
|
||||
);
|
||||
}
|
||||
|
||||
#[allow(dead_code)] // This is not used in every test
|
||||
pub fn the_same<V>(element: V)
|
||||
where
|
||||
V: bincode::enc::Encodeable + bincode::de::Decodable + PartialEq + Debug + 'static,
|
||||
{
|
||||
the_same_with_comparer(element, |a, b| a == b);
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue