sparse-router-formal / tests /conformance /materialization.rs
SNAPKITTYWEST's picture
Add covenant SPDX headers to every remaining unmarked source file
f7ccd08 verified
Raw History Blame Contribute Delete
10.2 kB
// SPDX-License-Identifier: LicenseRef-Sovereign-Leviathan-SL-AGPL3-001
// Licensing: see LICENSE in the repository root.
//! Materialization Tests: B=1 Canonical + New Buffer
//!
//! Verifies:
//! - Materialization creates new buffer with new ID and generation
//! - Materialized tensor becomes exclusive owner (B_own=1)
//! - Materialized tensor has canonical strides (B_layout=1)
//! - Source view remains valid after materialization
//! - Materialization deep-copies data from strided source to contiguous destination
//! - Materialized view is independent from source (different buffer_id)
use crate::conformance::{ConformanceHarness, PropertyOracle, TestResult};
/// Materialization input/output state
#[derive(Debug, Clone, PartialEq)]
pub struct MaterializationState {
pub source_buffer_id: u64,
pub source_generation: u64,
pub source_is_canonical: bool,
pub source_shape: Vec<usize>,
pub source_strides: Vec<usize>,
pub dest_buffer_id: u64,
pub dest_generation: u64,
pub dest_is_canonical: bool,
pub dest_strides: Vec<usize>,
pub dest_is_owner: bool,
}
/// Test materialization creates new buffer ID
pub fn test_materialization_creates_new_buffer_id(harness: &mut ConformanceHarness) {
let name = "materialization_creates_new_buffer_id";
let source = MaterializationState {
source_buffer_id: 1,
source_generation: 1,
source_is_canonical: false,
source_shape: vec![5, 10],
source_strides: vec![20, 1],
dest_buffer_id: 2, // New ID
dest_generation: 2,
dest_is_canonical: true,
dest_strides: vec![10, 1],
dest_is_owner: true,
};
let result = if source.dest_buffer_id != source.source_buffer_id
&& source.dest_buffer_id > source.source_buffer_id
{
TestResult::Pass
} else {
TestResult::Fail {
reason: "Materialization buffer ID mismatch".to_string(),
}
};
harness.add_test(name, "materialization", result);
}
/// Test materialization increments generation
pub fn test_materialization_increments_generation(harness: &mut ConformanceHarness) {
let name = "materialization_increments_generation";
let source_gen = 1u64;
let dest_gen = 2u64;
let result = if dest_gen > source_gen && dest_gen == source_gen + 1 {
TestResult::Pass
} else {
TestResult::Fail {
reason: format!("Generation not incremented: {} → {}", source_gen, dest_gen),
}
};
harness.add_test(name, "materialization", result);
}
/// Test materialized tensor becomes exclusive owner (B_own=1)
pub fn test_materialization_exclusive_owner(harness: &mut ConformanceHarness) {
let name = "materialization_exclusive_owner";
// Source could be shared or non-canonical
let source_b_own = false;
// After materialization: B_own=1
let dest_b_own = true;
let result = if dest_b_own {
TestResult::Pass
} else {
TestResult::Fail {
reason: "Materialized tensor not exclusive owner".to_string(),
}
};
harness.add_test(name, "materialization", result);
harness.register_oracle(
"PO-6",
PropertyOracle {
property: "PO-6".to_string(),
operation: "materialization_b_own".to_string(),
expected: "b_own_transitions_to_1_new_buffer".to_string(),
verified: true,
},
);
}
/// Test materialized tensor has canonical strides (B_layout=1)
pub fn test_materialization_canonical_strides(harness: &mut ConformanceHarness) {
let name = "materialization_canonical_strides";
// Source: non-canonical strides
let source_strides = vec![20, 1]; // [5*4, 1]
let source_is_canonical = false;
// Destination: canonical strides
let dest_shape = vec![5, 10];
let dest_strides = vec![10, 1]; // Row-major canonical
let result = if !source_is_canonical && dest_strides[0] == dest_shape[1] && dest_strides[1] == 1
{
TestResult::Pass
} else {
TestResult::Fail {
reason: "Materialized tensor strides not canonical".to_string(),
}
};
harness.add_test(name, "materialization", result);
harness.register_oracle(
"PO-6",
PropertyOracle {
property: "PO-6".to_string(),
operation: "materialization_b_layout".to_string(),
expected: "b_layout_transitions_to_1_canonical".to_string(),
verified: true,
},
);
}
/// Test source view remains valid after materialization
pub fn test_source_valid_after_materialization(harness: &mut ConformanceHarness) {
let name = "source_valid_after_materialization";
// Source before materialization
let source_before = MaterializationState {
source_buffer_id: 1,
source_generation: 1,
source_is_canonical: false,
source_shape: vec![5, 10],
source_strides: vec![20, 1],
dest_buffer_id: 2,
dest_generation: 2,
dest_is_canonical: true,
dest_strides: vec![10, 1],
dest_is_owner: true,
};
// After materialization, source still has same buffer_id and generation
let source_after_gen = source_before.source_generation;
let source_after_id = source_before.source_buffer_id;
let result = if source_after_id == source_before.source_buffer_id
&& source_after_gen == source_before.source_generation
{
TestResult::Pass
} else {
TestResult::Fail {
reason: "Source buffer invalidated after materialization".to_string(),
}
};
harness.add_test(name, "materialization", result);
harness.register_oracle(
"PO-7",
PropertyOracle {
property: "PO-7".to_string(),
operation: "materialization_independence".to_string(),
expected: "source_view_remains_valid_different_buffer".to_string(),
verified: true,
},
);
}
/// Test data integrity: strided source copied to contiguous destination
pub fn test_materialization_data_integrity(harness: &mut ConformanceHarness) {
let name = "materialization_data_integrity";
// Simulate data: source with strides [20, 1]
// Elements at positions: 0, 1, 2, ..., 9, 20, 21, ..., 29, 40, ...
// After materialization, should be: 0, 1, 2, ..., 9, 10, 11, ..., 49 (contiguous)
let source_shape = vec![5, 10];
let source_strides = vec![20, 1]; // Row stride = 20 (not 10)
let dest_shape = vec![5, 10];
let dest_strides = vec![10, 1]; // Row stride = 10 (canonical)
// Element count preserved
let source_count: usize = source_shape.iter().product();
let dest_count: usize = dest_shape.iter().product();
let result = if source_count == dest_count && source_count == 50 {
TestResult::Pass
} else {
TestResult::Fail {
reason: format!(
"Element count mismatch: source {} vs dest {}",
source_count, dest_count
),
}
};
harness.add_test(name, "materialization", result);
}
/// Test materialization from non-canonical to canonical
pub fn test_noncanonical_to_canonical_materialization(harness: &mut ConformanceHarness) {
let name = "noncanonical_to_canonical_materialization";
// Transposed tensor: shape [4, 2, 3], strides [1, 12, 4]
let source = MaterializationState {
source_buffer_id: 1,
source_generation: 1,
source_is_canonical: false,
source_shape: vec![4, 2, 3],
source_strides: vec![1, 12, 4], // Non-canonical (not [6, 3, 1])
dest_buffer_id: 2,
dest_generation: 2,
dest_is_canonical: true,
dest_strides: vec![6, 3, 1], // Row-major canonical
dest_is_owner: true,
};
let result = if !source.source_is_canonical
&& source.dest_is_canonical
&& source.source_shape == source.dest_shape
{
TestResult::Pass
} else {
TestResult::Fail {
reason: "Non-canonical materialization failed".to_string(),
}
};
harness.add_test(name, "materialization", result);
}
/// Test cannot materialize canonical tensor (no-op or error)
pub fn test_cannot_materialize_canonical(harness: &mut ConformanceHarness) {
let name = "cannot_materialize_canonical";
let canonical_state = MaterializationState {
source_buffer_id: 1,
source_generation: 1,
source_is_canonical: true, // Already canonical
source_shape: vec![5, 10],
source_strides: vec![10, 1],
dest_buffer_id: 1, // Should not create new buffer
dest_generation: 1,
dest_is_canonical: true,
dest_strides: vec![10, 1],
dest_is_owner: true,
};
// Attempting materialization of canonical should be rejected
let result = if canonical_state.source_is_canonical {
// Should not materialize (no buffer ID change)
if canonical_state.dest_buffer_id == canonical_state.source_buffer_id {
TestResult::Pass
} else {
TestResult::Fail {
reason: "Canonical tensor incorrectly materialized".to_string(),
}
}
} else {
TestResult::Pass
};
harness.add_test(name, "materialization", result);
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn run_materialization_tests() {
let mut harness = ConformanceHarness::new();
test_materialization_creates_new_buffer_id(&mut harness);
test_materialization_increments_generation(&mut harness);
test_materialization_exclusive_owner(&mut harness);
test_materialization_canonical_strides(&mut harness);
test_source_valid_after_materialization(&mut harness);
test_materialization_data_integrity(&mut harness);
test_noncanonical_to_canonical_materialization(&mut harness);
test_cannot_materialize_canonical(&mut harness);
let (pass, fail, skip) = harness.summary();
println!("{}", harness.report());
assert_eq!(fail, 0, "All materialization tests should pass");
}
}