use std::env;
use std::path::PathBuf;
#[cfg(feature = "dynamic-native-runtime")]
#[path = "runtime_events_native/evidence.rs"]
mod evidence;
#[cfg(feature = "dynamic-native-runtime")]
#[path = "runtime_events_native/families.rs"]
mod families;
#[cfg(feature = "dynamic-native-runtime")]
#[path = "runtime_events_native/family_coverage.rs"]
mod family_coverage;
#[cfg(feature = "dynamic-native-runtime")]
#[path = "runtime_events_native/libraries.rs"]
mod libraries;
#[cfg(feature = "dynamic-native-runtime")]
#[path = "runtime_events_native/model_open_checks.rs"]
mod model_open_checks;
const GATE_ENV: &str = "MESH_LLM_RUNTIME_EVENTS_NATIVE_TEST";
#[cfg(feature = "dynamic-native-runtime")]
const BUNDLE_DIR_ENV: &str = "MESH_LLM_NATIVE_RUNTIME_BUNDLE_DIR";
#[cfg(feature = "dynamic-native-runtime")]
const MODEL_ENV: &str = "MESH_LLM_RUNTIME_EVENTS_MODEL";
const EVIDENCE_FILE_ENV: &str = "MESH_LLM_RUNTIME_EVENTS_EVIDENCE_FILE";
fn write_marker(path: Option<&std::path::Path>, line: &str) {
skippy_runtime::write_evidence_marker(path, line);
}
#[test]
fn runtime_events_native_gate() {
let evidence_path = env::var_os(EVIDENCE_FILE_ENV).map(PathBuf::from);
if env::var(GATE_ENV).ok().as_deref() != Some("1") {
println!("BLOCKED: {GATE_ENV} unset");
write_marker(
evidence_path.as_deref(),
"blocked-when-ungated: gate unset, no native symbol was touched",
);
return;
}
#[cfg(not(feature = "dynamic-native-runtime"))]
{
println!("BLOCKED: dynamic-native-runtime feature not enabled");
write_marker(
evidence_path.as_deref(),
"blocked: dynamic-native-runtime feature is not enabled for this run",
);
panic!("{GATE_ENV}=1 requires the dynamic-native-runtime feature");
}
#[cfg(feature = "dynamic-native-runtime")]
{
run_real_native_gate(evidence_path);
}
}
#[cfg(feature = "dynamic-native-runtime")]
fn required_env(name: &str, evidence_path: &std::path::Path, purpose: &str) -> String {
env::var(name).unwrap_or_else(|_| {
println!("BLOCKED: {name} unset");
write_marker(
Some(evidence_path),
&format!("blocked: {name} unset, required when {GATE_ENV}=1"),
);
panic!("{GATE_ENV}=1 requires {name} to {purpose}")
})
}
#[cfg(feature = "dynamic-native-runtime")]
fn run_real_native_gate(evidence_path: Option<PathBuf>) {
let evidence_path = evidence_path.unwrap_or_else(|| {
panic!("{GATE_ENV}=1 requires {EVIDENCE_FILE_ENV} to name the evidence file")
});
let bundle_dir = required_env(
BUNDLE_DIR_ENV,
&evidence_path,
"point at a dynamic native runtime",
);
let model_path = required_env(MODEL_ENV, &evidence_path, "name a readable model");
let evidence = evidence::Evidence::new(evidence_path);
let outcome = std::panic::catch_unwind(std::panic::AssertUnwindSafe(|| {
gated_steps(&PathBuf::from(bundle_dir), &model_path, &evidence);
}));
match outcome {
Ok(()) => evidence.flush_executed(),
Err(payload) => {
skippy_runtime::clear_runtime_event_reporter();
let reason = payload
.downcast_ref::<String>()
.map(String::as_str)
.or_else(|| payload.downcast_ref::<&str>().copied())
.unwrap_or("non-string panic");
evidence.flush_failed(reason.lines().next().unwrap_or(reason));
std::panic::resume_unwind(payload);
}
}
}
#[cfg(feature = "dynamic-native-runtime")]
fn load_runtime(bundle_dir: &std::path::Path) -> skippy_runtime::CapabilityReport {
let libraries = libraries::discover_libraries(bundle_dir);
assert!(
!libraries.is_empty(),
"no native runtime libraries found under {}",
bundle_dir.display()
);
if !skippy_runtime::native_runtime_loaded() {
unsafe { skippy_runtime::load_native_runtime_libraries(&libraries) }
.expect("load native runtime libraries for the real ABI admission test");
}
skippy_runtime::probe_capabilities()
}
#[cfg(feature = "dynamic-native-runtime")]
fn gated_steps(bundle_dir: &std::path::Path, model_path: &str, evidence: &evidence::Evidence) {
use families::{FamilyTally, drain_global};
let report = load_runtime(bundle_dir);
evidence.record(
"exact-abi-admission: native runtime loaded (loader enforces exact major.minor.patch)",
);
evidence.record(format!(
"capability-probe: confirmed={:#x} health_messages={}",
report.confirmed,
report.health_messages.len()
));
assert!(
report.family_confirmed(skippy_ffi::FEATURE_RUNTIME_EVENTS),
"capability probe must confirm FEATURE_RUNTIME_EVENTS on this runtime"
);
evidence.record(format!(
"runtime-events-feature-bit: confirmed (FEATURE_RUNTIME_EVENTS={:#x})",
skippy_ffi::FEATURE_RUNTIME_EVENTS
));
evidence.record(
"mixed-version-fallback: unit-covered by runtime_events::tests::\
queue_supplied_but_events_unsupported_takes_legacy_path_and_queue_stays_empty and \
assert_model_open_events_feature_missing_falls_back; not reachable in this process \
because the loaded runtime advertises FEATURE_RUNTIME_EVENTS",
);
let _ = drain_global();
assert!(
skippy_runtime::install_runtime_event_reporter(),
"runtime event reporter must install when the explicit native gate is enabled"
);
evidence.record("reporter-install: true");
let config = skippy_runtime::RuntimeConfig::default();
let mut tally = FamilyTally::default();
let structured =
family_coverage::run_load_session_unload(model_path, &config, evidence, &mut tally);
assert!(
structured > 0,
"successful model-open must produce at least one structured production callback; \
old model-open progress alone is insufficient"
);
evidence.record(format!("structured-production-callbacks: {structured}"));
model_open_checks::check_successful_opens(model_path, &config, evidence, &mut tally);
model_open_checks::check_failed_opens(&config, evidence, &mut tally);
let missing = family_coverage::judge_family_coverage(&report, &tally, evidence);
evidence.record(format!(
"global-reporter: dropped={} rejected={}",
skippy_runtime::dropped_runtime_events(),
skippy_runtime::rejected_runtime_events()
));
skippy_runtime::clear_runtime_event_reporter();
evidence.record("reporter-clear: returned");
assert!(
missing.is_empty(),
"confirmed families never observed during a real load + session + unload: {missing:?}"
);
}