oct 0.36.2

Octonary transcodings.
Documentation
// Copyright 2024-2026 Gabriel Bjørnager Jensen.
//
// SPDX: MIT OR Apache-2.0

//! Tests for [`Deserialise`].

#![cfg(test)]

use core::char;
use oct::serdes::Deserialise;

#[cfg(feature = "alloc")]
use alloc::borrow::Cow;

#[cfg(feature = "alloc")]
use alloc::boxed::Box;

#[cfg(feature = "alloc")]
use alloc::rc::Rc;

#[cfg(feature = "alloc")]
use alloc::string::String;

#[cfg(all(feature = "alloc", feature = "bstr"))]
use alloc::bstr::ByteString;

#[cfg(all(feature = "alloc", feature = "bstr"))]
use core::bstr::ByteStr;

#[cfg(all(feature = "alloc", target_has_atomic = "ptr"))]
use alloc::sync::Arc;

#[test]
fn test_deserialise() {
	assert_eq!(
		i8::deserialise(&mut [0x00].as_slice()).unwrap(),
		0x00,
	);

	assert_eq!(
		i8::deserialise(&mut [0x7F].as_slice()).unwrap(),
		0x7F,
	);

	assert_eq!(
		i8::deserialise(&mut [0x80].as_slice()).unwrap(),
		-0x80,
	);

	assert_eq!(
		i8::deserialise(&mut [0xFF].as_slice()).unwrap(),
		-0x01,
	);

	assert_eq!(
		i16::deserialise(&mut [0x00, 0x00].as_slice()).unwrap(),
		0x0000,
	);

	assert_eq!(
		i16::deserialise(&mut [0xFF, 0x7F].as_slice()).unwrap(),
		0x7FFF,
	);

	assert_eq!(
		i16::deserialise(&mut [0x00, 0x80].as_slice()).unwrap(),
		-0x8000,
	);

	assert_eq!(
		i16::deserialise(&mut [0xFF, 0xFF].as_slice()).unwrap(),
		-0x0001,
	);

	assert_eq!(
		i32::deserialise(&mut [0x00, 0x00, 0x00, 0x00].as_slice()).unwrap(),
		0x00000000,
	);

	assert_eq!(
		i32::deserialise(&mut [0xFF, 0xFF, 0xFF, 0x7F].as_slice()).unwrap(),
		0x7FFFFFFF,
	);

	assert_eq!(
		i32::deserialise(&mut [0x00, 0x00, 0x00, 0x80].as_slice()).unwrap(),
		-0x80000000,
	);

	assert_eq!(
		i32::deserialise(&mut [0xFF, 0xFF, 0xFF, 0xFF].as_slice()).unwrap(),
		-0x00000001,
	);

	assert_eq!(
		i64::deserialise(&mut [0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00].as_slice()).unwrap(),
		0x0000000000000000,
	);

	assert_eq!(
		i64::deserialise(&mut [0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x7F].as_slice()).unwrap(),
		0x7FFFFFFFFFFFFFFF,
	);

	assert_eq!(
		i64::deserialise(&mut [0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80].as_slice()).unwrap(),
		-0x8000000000000000,
	);

	assert_eq!(
		i64::deserialise(&mut [0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF].as_slice()).unwrap(),
		-0x0000000000000001,
	);

	assert_eq!(
		u128::deserialise(&mut [
			0x7F, 0x8F, 0x6F, 0x9F, 0x5F, 0xAF, 0x4F, 0xBF,
			0x3F, 0xCF, 0x2F, 0xDF, 0x1F, 0xEF, 0x0F, 0xFF,
		].as_slice()).unwrap(),
		0xFF_0F_EF_1F_DF_2F_CF_3F_BF_4F_AF_5F_9F_6F_8F_7F,
	);

	assert_eq!(
		char::deserialise(&mut [0xFD, 0xFF, 0x00, 0x00].as_slice()).unwrap(),
		char::REPLACEMENT_CHARACTER,
	);

	assert_eq!(
		<[char; 5]>::deserialise(&mut [
			0xBB, 0x03, 0x00, 0x00, 0x91, 0x03, 0x00, 0x00,
			0xBC, 0x03, 0x00, 0x00, 0x94, 0x03, 0x00, 0x00,
			0xB1, 0x03, 0x00, 0x00,
		].as_slice()).unwrap(),
		['\u{03BB}', '\u{0391}', '\u{03BC}', '\u{0394}', '\u{03B1}'],
	);

	assert_eq!(
		Option::<()>::deserialise(&mut [0x00].as_slice()).unwrap(),
		None,
	);

	assert_eq!(
		Option::<()>::deserialise(&mut [0x01].as_slice()).unwrap(),
		Some(()),
	);

	assert_eq!(
		Result::<(), i8>::deserialise(&mut [0x00, 0x00].as_slice()).unwrap(),
		Ok(()),
	);

	assert_eq!(
		Result::<(), i8>::deserialise(&mut [0x01, 0x7F].as_slice()).unwrap(),
		Err(i8::MAX),
	);
}

#[cfg(all(feature = "alloc", feature = "bstr"))]
#[test]
fn test_deserialise_bstr() {
	let data = [
		0x10, 0x00,
		b'I',
		b' ',
		b'L',
		b'O',
		b'V',
		b'E',
		b' ',
		b'Y',
		b'O',
		b'U',
		b'!',
		b'!',
		b'!',
		b' ',
		b'<',
		b'3',
	];

	assert_eq!(
		ByteString::deserialise(&mut data.as_slice()).unwrap().0,
		b"I LOVE YOU!!! <3",
	);

	assert_eq!(
		&Box::<ByteStr>::deserialise(&mut data.as_slice()).unwrap().0,
		b"I LOVE YOU!!! <3",
	);

	assert_eq!(
		&Rc::<ByteStr>::deserialise(&mut data.as_slice()).unwrap().0,
		b"I LOVE YOU!!! <3",
	);

	#[cfg(target_has_atomic = "ptr")]
	assert_eq!(
		&Arc::<ByteStr>::deserialise(&mut data.as_slice()).unwrap().0,
		b"I LOVE YOU!!! <3",
	);
}

#[cfg(feature = "alloc")]
#[test]
fn test_deserialise_str_compatible() {
	let buf = b"\x08\x00HEDGEHOG";

	let value = "HEDGEHOG";

	#[cfg(all(feature = "alloc", target_has_atomic = "ptr"))]
	assert_eq!(
		&*Arc::<str>::deserialise(&mut buf.as_slice()).unwrap(),
		value,
	);

	#[cfg(all(feature = "alloc", target_has_atomic = "ptr"))]
	assert_eq!(
		&*Arc::<String>::deserialise(&mut buf.as_slice()).unwrap(),
		value,
	);

	#[cfg(feature = "alloc")]
	assert_eq!(
		&*Box::<str>::deserialise(&mut buf.as_slice()).unwrap(),
		value,
	);

	#[cfg(feature = "alloc")]
	assert_eq!(
		&*Box::<String>::deserialise(&mut buf.as_slice()).unwrap(),
		value,
	);

	#[cfg(feature = "alloc")]
	assert_eq!(
		&*Cow::<'static, str>::deserialise(&mut buf.as_slice()).unwrap(),
		value,
	);

	#[cfg(feature = "alloc")]
	assert_eq!(
		&*Cow::<'static, String>::deserialise(&mut buf.as_slice()).unwrap(),
		value,
	);

	#[cfg(feature = "alloc")]
	assert_eq!(
		&*Rc::<str>::deserialise(&mut buf.as_slice()).unwrap(),
		value,
	);

	#[cfg(feature = "alloc")]
	assert_eq!(
		&*Rc::<String>::deserialise(&mut buf.as_slice()).unwrap(),
		value,
	);

	#[cfg(feature = "alloc")]
	assert_eq!(
		String::deserialise(&mut buf.as_slice()).unwrap(),
		value,
	);
}

#[cfg(feature = "proc_macro")]
#[test]
fn test_derive_deserialise() {
	#[derive(Debug, Deserialise, PartialEq)]
	struct ProcExit {
		exit_code: i32,
		timestmap: u64,
	}

	#[derive(Debug, Deserialise, PartialEq)]
	struct NewByte(u8);

	#[derive(Debug, Deserialise, PartialEq)]
	struct Unit;

	#[derive(Debug, Deserialise, PartialEq)]
	enum UnitOrFields {
		Unit,
		Unnamed(i32),
		Named { timestamp: u64 },
	}

	assert_eq!(
		ProcExit::deserialise(&mut [
			0x01, 0x00, 0x00, 0x00, 0x00, 0xE1, 0x0B, 0x5E,
			0x00, 0x00, 0x00, 0x00,
		].as_slice()).unwrap(),
		ProcExit { exit_code: 0x1, timestmap: 1577836800 },
	);

	assert_eq!(
		NewByte::deserialise(&mut [0x80].as_slice()).unwrap(),
		NewByte(0x80),
	);

	assert_eq!(
		Unit::deserialise(&mut [].as_slice()).unwrap(),
		Unit,
	);

	assert_eq!(
		UnitOrFields::deserialise(&mut [0x00].as_slice()).unwrap(),
		UnitOrFields::Unit,
	);

	assert_eq!(
		UnitOrFields::deserialise(&mut [0x01, 0xFF, 0xFF, 0xFF, 0xFF].as_slice()).unwrap(),
		UnitOrFields::Unnamed(-1),
	);

	assert_eq!(
		UnitOrFields::deserialise(&mut [
			0x02, 0x4C, 0xC8, 0xC5, 0x66, 0x00, 0x00, 0x00,
			0x00,
		].as_slice()).unwrap(),
		UnitOrFields::Named { timestamp: 1724237900 },
	);

	UnitOrFields::deserialise(&mut [0x03].as_slice()).unwrap_err();
}