use core::fmt;
#[derive(Debug, Clone, PartialEq, Eq)]
pub struct LimitsError {
pub context: &'static str,
pub max: usize,
pub got: usize,
}
impl fmt::Display for LimitsError {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(
f,
"超过资源上限 ({}): 允许至多 {}, 实际 {}",
self.context, self.max, self.got
)
}
}
impl core::error::Error for LimitsError {}
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub struct VerifyLimits {
pub max_elf_bytes: usize,
pub max_ta_signature_section_bytes: usize,
pub max_plain_output_bytes: usize,
pub max_cms_der_bytes: usize,
pub max_embedded_certificates: usize,
pub max_certificate_der_bytes: usize,
pub max_total_embedded_cert_der_bytes: usize,
pub max_section_headers: usize,
pub max_program_headers: usize,
}
impl Default for VerifyLimits {
fn default() -> Self {
Self::recommended()
}
}
impl VerifyLimits {
pub const fn recommended() -> Self {
Self {
max_elf_bytes: 64 * 1024 * 1024,
max_ta_signature_section_bytes: 4 * 1024 * 1024,
max_plain_output_bytes: 96 * 1024 * 1024,
max_cms_der_bytes: 8 * 1024 * 1024,
max_embedded_certificates: 32,
max_certificate_der_bytes: 256 * 1024,
max_total_embedded_cert_der_bytes: 512 * 1024,
max_section_headers: 65536,
max_program_headers: 4096,
}
}
pub fn check_elf_input_len(&self, got: usize) -> Result<(), LimitsError> {
if got > self.max_elf_bytes {
Err(LimitsError {
context: "ELF 输入长度",
max: self.max_elf_bytes,
got,
})
} else {
Ok(())
}
}
pub fn check_ta_signature_payload_len(&self, got: usize) -> Result<(), LimitsError> {
if got > self.max_ta_signature_section_bytes {
Err(LimitsError {
context: ".ta_signature 节长度",
max: self.max_ta_signature_section_bytes,
got,
})
} else {
Ok(())
}
}
pub fn check_plain_buffer_len(&self, got: usize) -> Result<(), LimitsError> {
if got > self.max_plain_output_bytes {
Err(LimitsError {
context: "plain 缓冲区长度",
max: self.max_plain_output_bytes,
got,
})
} else {
Ok(())
}
}
pub fn check_cms_der_len(&self, got: usize) -> Result<(), LimitsError> {
if got > self.max_cms_der_bytes {
Err(LimitsError {
context: "CMS/PKCS#7 DER 长度",
max: self.max_cms_der_bytes,
got,
})
} else {
Ok(())
}
}
pub fn check_section_header_count(&self, got: usize) -> Result<(), LimitsError> {
if got > self.max_section_headers {
Err(LimitsError {
context: "ELF 节头数量",
max: self.max_section_headers,
got,
})
} else {
Ok(())
}
}
pub fn check_program_header_count(&self, got: usize) -> Result<(), LimitsError> {
if got > self.max_program_headers {
Err(LimitsError {
context: "ELF 程序头数量",
max: self.max_program_headers,
got,
})
} else {
Ok(())
}
}
}