liblitho 0.2.0

cli tool to flash/clone the images to storage devices
Documentation
//! Block-device open handles: platform-specific readers and writers.

use anyhow::Result;
use std::io::{Read, Write};

/// Trait for reading from a device in a platform-specific way.
pub trait DeviceReader: Read {
    /// Open a device for reading.
    fn open(device_path: &str) -> Result<Self>
    where
        Self: Sized;

    /// Size of the device in bytes.
    fn device_size(&self) -> Result<u64>;
}

/// Trait for writing to a device in a platform-specific way.
pub trait DeviceWriter: Write {
    /// Open a device for writing.
    fn open(device_path: &str) -> Result<Self>
    where
        Self: Sized;

    /// Flush and sync so data is durable on the device.
    fn flush_and_sync(&mut self) -> Result<()>;

    /// Whether the writer can durably sync ranges during the write loop.
    fn supports_incremental_sync(&self) -> bool {
        false
    }

    /// Durably sync a byte range already written to the device.
    fn sync_written_range(&mut self, offset: u64, len: u64) -> Result<()> {
        let _ = (offset, len);
        Ok(())
    }

    /// Flush and sync, reporting progress as ranges complete.
    fn flush_and_sync_with_progress(
        &mut self,
        sync_bytes: u64,
        mut on_progress: Option<&mut dyn FnMut(u64, u64)>,
    ) -> Result<()> {
        if let Some(callback) = on_progress.as_mut() {
            callback(0, sync_bytes);
        }
        self.flush_and_sync()?;
        if let Some(callback) = on_progress.as_mut() {
            callback(sync_bytes, sync_bytes);
        }
        Ok(())
    }

    /// Size of the device in bytes.
    fn device_size(&self) -> Result<u64>;

    /// Write bytes at an absolute byte offset on the device.
    fn write_at(&mut self, offset: u64, buf: &[u8]) -> Result<()> {
        let _ = (offset, buf);
        anyhow::bail!("write_at is not supported on this platform")
    }

    /// Whether post-write verification can read back through this open handle.
    fn supports_inline_verify(&self) -> bool {
        false
    }

    /// Rewind the device offset before inline verification.
    fn rewind_for_verify(&mut self) -> Result<()> {
        anyhow::bail!("rewind_for_verify is not supported on this platform")
    }

    /// Read bytes during inline verification.
    fn read_for_verify(&mut self, buf: &mut [u8]) -> std::io::Result<usize> {
        let _ = buf;
        Err(std::io::Error::new(
            std::io::ErrorKind::Unsupported,
            "read_for_verify is not supported on this platform",
        ))
    }
}