20260512 完成CCR CIR行为差异实验能力

This commit is contained in:
2026-05-13 05:11:17 +08:00
parent f2fbb20a29
commit 137b3516d0
8 changed files with 3775 additions and 7 deletions

View File

@@ -189,12 +189,55 @@ pub fn process_publication_point_for_issuer_with_options<P: PublicationPointData
let mut audit: Vec<ObjectAuditEntry> = Vec::new();
// Enforce that `manifest_bytes` is actually a manifest object.
let _manifest = ManifestObject::decode_der_with_strict_options(
let _manifest = match ManifestObject::decode_der_with_strict_options(
manifest_bytes,
policy.strict.cms_der,
policy.strict.name,
)
.expect("publication point snapshot manifest decodes");
) {
Ok(manifest) => manifest,
Err(e) => {
stats.publication_point_dropped = true;
warnings.push(
Warning::new(format!(
"dropping publication point: manifest decode failed: {e}"
))
.with_rfc_refs(&[
RfcRef("RFC 9286 §4"),
RfcRef("RFC 9286 §6.2"),
RfcRef("RFC 9286 §6.6"),
])
.with_context(manifest_rsync_uri),
);
for f in locked_files {
if f.rsync_uri.ends_with(".roa") {
audit.push(ObjectAuditEntry {
rsync_uri: f.rsync_uri.clone(),
sha256_hex: sha256_hex_from_32(&f.sha256),
kind: AuditObjectKind::Roa,
result: AuditObjectResult::Skipped,
detail: Some("skipped: manifest decode failed".to_string()),
});
} else if f.rsync_uri.ends_with(".asa") {
audit.push(ObjectAuditEntry {
rsync_uri: f.rsync_uri.clone(),
sha256_hex: sha256_hex_from_32(&f.sha256),
kind: AuditObjectKind::Aspa,
result: AuditObjectResult::Skipped,
detail: Some("skipped: manifest decode failed".to_string()),
});
}
}
return ObjectsOutput {
vrps: Vec::new(),
aspas: Vec::new(),
router_keys: Vec::new(),
local_outputs_cache: Vec::new(),
warnings,
stats,
audit,
};
}
};
// Decode issuer CA once; if it fails we cannot validate ROA/ASPA EE certificates.
let issuer_ca = match decode_resource_certificate_with_policy(issuer_ca_der, policy) {
@@ -978,12 +1021,55 @@ pub(crate) fn prepare_publication_point_for_parallel_roa<P: PublicationPointData
.count();
let mut audit: Vec<ObjectAuditEntry> = Vec::new();
let _manifest = ManifestObject::decode_der_with_strict_options(
let _manifest = match ManifestObject::decode_der_with_strict_options(
manifest_bytes,
policy.strict.cms_der,
policy.strict.name,
)
.expect("publication point snapshot manifest decodes");
) {
Ok(manifest) => manifest,
Err(e) => {
stats.publication_point_dropped = true;
warnings.push(
Warning::new(format!(
"dropping publication point: manifest decode failed: {e}"
))
.with_rfc_refs(&[
RfcRef("RFC 9286 §4"),
RfcRef("RFC 9286 §6.2"),
RfcRef("RFC 9286 §6.6"),
])
.with_context(manifest_rsync_uri),
);
for f in locked_files {
if f.rsync_uri.ends_with(".roa") {
audit.push(ObjectAuditEntry {
rsync_uri: f.rsync_uri.clone(),
sha256_hex: sha256_hex_from_32(&f.sha256),
kind: AuditObjectKind::Roa,
result: AuditObjectResult::Skipped,
detail: Some("skipped: manifest decode failed".to_string()),
});
} else if f.rsync_uri.ends_with(".asa") {
audit.push(ObjectAuditEntry {
rsync_uri: f.rsync_uri.clone(),
sha256_hex: sha256_hex_from_32(&f.sha256),
kind: AuditObjectKind::Aspa,
result: AuditObjectResult::Skipped,
detail: Some("skipped: manifest decode failed".to_string()),
});
}
}
return ParallelObjectsPrepare::Complete(ObjectsOutput {
vrps: Vec::new(),
aspas: Vec::new(),
router_keys: Vec::new(),
local_outputs_cache: Vec::new(),
warnings,
stats,
audit,
});
}
};
let issuer_ca = match decode_resource_certificate_with_policy(issuer_ca_der, policy) {
Ok(v) => v,
@@ -2403,7 +2489,11 @@ mod tests {
Afi, AsIdOrRange, AsIdentifierChoice, IpAddressFamily, IpAddressOrRange, IpAddressRange,
IpPrefix, IpResourceSet,
};
use crate::policy::Policy;
use crate::storage::PackTime;
use crate::validation::publication_point::PublicationPointSnapshot;
use std::collections::HashMap;
use time::OffsetDateTime;
fn fixture_bytes(path: &str) -> Vec<u8> {
std::fs::read(std::path::PathBuf::from(env!("CARGO_MANIFEST_DIR")).join(path))
@@ -2874,4 +2964,41 @@ mod tests {
assert_eq!(roa_afi_to_string(RoaAfi::Ipv4), "ipv4");
assert_eq!(roa_afi_to_string(RoaAfi::Ipv6), "ipv6");
}
#[test]
fn strict_name_manifest_decode_failure_drops_publication_point() {
let publication_point = PublicationPointSnapshot {
format_version: PublicationPointSnapshot::FORMAT_VERSION_V1,
manifest_rsync_uri: "rsync://example.test/repo/manifest.mft".to_string(),
publication_point_rsync_uri: "rsync://example.test/repo/".to_string(),
manifest_number_be: vec![0x01],
this_update: PackTime::from_utc_offset_datetime(OffsetDateTime::now_utc()),
next_update: PackTime::from_utc_offset_datetime(OffsetDateTime::now_utc()),
verified_at: PackTime::from_utc_offset_datetime(OffsetDateTime::now_utc()),
manifest_bytes: vec![0x01, 0x02, 0x03],
files: vec![],
};
let policy = Policy::default();
let output = process_publication_point_for_issuer_with_options(
&publication_point,
&policy,
&[],
None,
None,
None,
OffsetDateTime::now_utc(),
None,
false,
);
assert!(output.stats.publication_point_dropped);
assert!(output.vrps.is_empty());
assert!(
output
.warnings
.iter()
.any(|warning| warning.message.contains("manifest decode failed")),
"{:?}",
output.warnings
);
}
}