Skip to main content

rvf_kernel/
error.rs

1//! Error types for the rvf-kernel crate.
2
3use std::fmt;
4use std::io;
5use std::path::PathBuf;
6
7/// Errors that can occur during kernel building, verification, or embedding.
8#[derive(Debug)]
9pub enum KernelError {
10    /// I/O error reading or writing kernel artifacts.
11    Io(io::Error),
12    /// The file at the given path is not a valid kernel image.
13    InvalidImage {
14        path: PathBuf,
15        reason: String,
16    },
17    /// The kernel image is too small to contain required headers.
18    ImageTooSmall {
19        size: u64,
20        min_size: u64,
21    },
22    /// SHA3-256 hash of extracted kernel does not match the stored hash.
23    HashMismatch {
24        expected: [u8; 32],
25        actual: [u8; 32],
26    },
27    /// Docker is not available or the build failed.
28    DockerBuildFailed(String),
29    /// The initramfs archive could not be built.
30    InitramfsBuildFailed(String),
31    /// Compression or decompression failed.
32    CompressionFailed(String),
33    /// A required configuration option is missing.
34    MissingConfig(String),
35    /// The kernel config string is invalid or missing required options.
36    InvalidConfig(String),
37    /// No KERNEL_SEG found in the RVF store.
38    NoKernelSegment,
39}
40
41impl fmt::Display for KernelError {
42    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
43        match self {
44            Self::Io(e) => write!(f, "kernel I/O error: {e}"),
45            Self::InvalidImage { path, reason } => {
46                write!(f, "invalid kernel image at {}: {reason}", path.display())
47            }
48            Self::ImageTooSmall { size, min_size } => {
49                write!(f, "kernel image too small: {size} bytes (minimum {min_size})")
50            }
51            Self::HashMismatch { expected, actual } => {
52                write!(
53                    f,
54                    "kernel hash mismatch: expected {}..., got {}...",
55                    hex_prefix(expected),
56                    hex_prefix(actual)
57                )
58            }
59            Self::DockerBuildFailed(msg) => write!(f, "Docker kernel build failed: {msg}"),
60            Self::InitramfsBuildFailed(msg) => write!(f, "initramfs build failed: {msg}"),
61            Self::CompressionFailed(msg) => write!(f, "compression failed: {msg}"),
62            Self::MissingConfig(msg) => write!(f, "missing kernel config: {msg}"),
63            Self::InvalidConfig(msg) => write!(f, "invalid kernel config: {msg}"),
64            Self::NoKernelSegment => write!(f, "no KERNEL_SEG found in RVF store"),
65        }
66    }
67}
68
69impl std::error::Error for KernelError {
70    fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
71        match self {
72            Self::Io(e) => Some(e),
73            _ => None,
74        }
75    }
76}
77
78impl From<io::Error> for KernelError {
79    fn from(e: io::Error) -> Self {
80        Self::Io(e)
81    }
82}
83
84fn hex_prefix(data: &[u8; 32]) -> String {
85    data.iter().take(4).map(|b| format!("{b:02x}")).collect()
86}