Skip to main content

native_ipc_testkit/
lib.rs

1#![doc = include_str!("../README.md")]
2
3use native_ipc_core::codec::{ENVELOPE_LEN, Envelope, Protocol, encode_message};
4
5/// Produces truncations of `input`, including the empty and complete input.
6pub fn every_truncation(input: &[u8]) -> impl Iterator<Item = &[u8]> {
7    (0..=input.len()).map(|len| &input[..len])
8}
9
10/// Produces at most `limit` deterministic one-bit hostile mutations.
11///
12/// The explicit limit keeps decoder corpora bounded in CI and downstream tests.
13pub fn bounded_bit_mutations(input: &[u8], limit: usize) -> Vec<Vec<u8>> {
14    input
15        .iter()
16        .enumerate()
17        .take(limit)
18        .map(|(index, _)| {
19            let mut mutated = input.to_vec();
20            mutated[index] ^= 1;
21            mutated
22        })
23        .collect()
24}
25
26/// Produces bounded hostile region-header/layout mutations at fixed fields.
27pub fn hostile_layout_mutations(valid_region: &[u8]) -> Vec<Vec<u8>> {
28    const OFFSETS: [usize; 12] = [0, 8, 12, 16, 56, 64, 68, 72, 80, 88, 96, 108];
29    OFFSETS
30        .into_iter()
31        .filter(|offset| *offset < valid_region.len())
32        .map(|offset| {
33            let mut mutated = valid_region.to_vec();
34            mutated[offset] ^= 1;
35            mutated
36        })
37        .collect()
38}
39
40/// Boundary values for hostile relative-offset and declared-length corpora.
41pub const HOSTILE_U64_BOUNDARIES: [u64; 7] = [0, 1, 71, 72, 127, u32::MAX as u64, u64::MAX];
42
43/// Encodes a message into an exactly sized owned golden vector.
44pub fn golden_message<P: Protocol>(
45    envelope: Envelope,
46    message: &P::Message,
47    payload_capacity: usize,
48) -> Result<Vec<u8>, native_ipc_core::codec::EncodeError> {
49    let total_capacity = ENVELOPE_LEN
50        .checked_add(payload_capacity)
51        .ok_or(native_ipc_core::codec::EncodeError::LengthOverflow)?;
52    let mut bytes = vec![0; total_capacity];
53    let written = encode_message::<P>(envelope, message, &mut bytes)?;
54    bytes.truncate(written);
55    Ok(bytes)
56}